【设计模式活用】之接口改造案例的设计思路(代理、适配器、工厂、模板方法)

我们在项目重构过程中,为了降低重构对线上的风险,会采用各种灰度机制,以提高系统稳定性;但是对于大量接口改造,我们在采用开关控制新接口与接口的切换,为了统一管理而采用集中管理机制。本文即例证一个重构案例,以说明我在重构方案设计中的设计思路,并以借鉴给读者用户。另外,本文采用了相关设计模式(代理、适配器、工厂、模板方法),以提高代码复用性和扩展性。

1.背景概述

本次系统重构,由于涉及到7个查询列表接口改造,意味着需要对接外部应用提供的接口。而原先对接前端的facade层存在大量冗余的代码,给系统迭代和后期维护增加了成本。同时,为了避免对facade层因为重构而带来代码修改的影响(因为未来这个facade将会被新的重构代码替换,以为着这个facade类需要废弃)。但是对于前端相关的查询接口,同时为了避免接口不兼容(譬如查询参数Form对象跟新接口不一致,查询结果跟新接口不一致)情况,需要采用一种适配模式,以便新接口对应查询接口的兼容。鉴于此,通过分析现状以及解决思路并通过相关设计模式的引入解决问题。

1.1 controller层

下图是目前controller层的相关接口清单,这是本次重构的接口清单一部分。
在这里插入图片描述

1.2 facade层

facade层包装了相关对接service层数据查询、转换等业务逻辑处理细节。
在这里插入图片描述

一个查询接口代码示例

public Result<PageVO<GpsQueryListVo>> queryListForInstalledOnApply(PageForm<GpsQueryListForm> form){
        List<GpsQueryListVo> carGpsReList = new ArrayList<>();
        int totalCount = 0;
        String LOG_TITLE = "车贷申请管理-GPS安装单列表";
        Boolean emptyFlag = StringUtils.isEmpty(form.getForm().getCustomerName()) ? Boolean.TRUE : Boolean.FALSE;
        try {
            if(StringTools.isNotEmpty(form.getForm().getBeginTime())){
                form.getForm().setBeginTime(form.getForm().getBeginTime() + " 00:00:00");
            }
            if(StringTools.isNotEmpty(form.getForm().getEndTime())){
                form.getForm().setEndTime(form.getForm().getEndTime() + " 23:59:59");
            }
            form.getForm().setBuzMark(QueryBuzMarkEnum.InstalledOnApply.getName());

            log.info("{},form={}",LOG_TITLE, JSON.toJSON(form));
            List<GpsQueryListVo>  proppserInfo;
            Map<String,String>  customerNameMap = null;
            if (StringTools.isNotEmpty(form.getForm().getCustomerName())){
                //根据查询条件中的客户姓名进行查找
                proppserInfo = proppserInfoService.listByForm(form.getForm());
                if (CollectionUtils.isEmpty(proppserInfo)){
                    log.info("{},根据appCode={} customerName={}未查询到信息",LOG_TITLE,form.getForm().getAppCode(),form.getForm().getCustomerName());
                    return Result.suc(PageVO.newInstance(totalCount,carGpsReList));
                }
                List<String> appCodes = proppserInfo.stream().map(GpsQueryListVo::getAppCode).collect(toList());
                form.getForm().setAppCodeList(appCodes);
                customerNameMap = proppserInfo.stream().collect(Collectors.toMap(GpsQueryListVo::getAppCode,GpsQueryListVo::getCustomerName));
            }
            carGpsReList = gpsQueryListService.queryListForInstalledOnApply(form);
            totalCount = gpsQueryListService.queryCountForInstalledOnApply(form);
            if(!carGpsReList.isEmpty()){
                List<String> appCodeScope = carGpsReList.stream().map(record -> record.getAppCode()).collect(toList());
                // 1、组装数据结构模型
                Map<String,List<CarGps>> gpsDeviceMap = getGpsDeviceListByAppCodes(appCodeScope);
                //为true时说明未查询过客户姓名
                if (emptyFlag){
                    // 查询客户姓名
                    List<Integer> proppserIds = carGpsReList.stream().map(record -> record.getProppserId()).collect(toList());
                    customerNameMap = getCustomerNameMap(proppserIds);
                }
                //2、设置相关属性
                for(GpsQueryListVo record : carGpsReList ) {
                    String appCode = record.getAppCode();
                    List<CarGps> carGpsList = gpsDeviceMap.getOrDefault(appCode,new ArrayList<>());
                    List<String> autoAuditResult = carGpsList.stream().map(CarGps::getAutoAuditResult).collect(toList()).stream().filter(list->!StringUtils.isEmpty(list)).collect(toList());
                    List<String> auditSupplement = carGpsList.stream().map(CarGps::getAuditSupplement).collect(toList()).stream().filter(list->!StringUtils.isEmpty(list)).collect(toList());
                    List<String> manualAuditResult = carGpsList.stream().map(CarGps::getManualAuditResult).collect(toList()).stream().filter(list->!StringUtils.isEmpty(list)).collect(toList());
                    record.setAutoAuditResult(StringUtils.collectionToDelimitedString(autoAuditResult,","));
                    record.setAuditSupplement(StringUtils.collectionToDelimitedString(auditSupplement,","));
                    record.setManualAuditResult(StringUtils.collectionToDelimitedString(manualAuditResult,","));
                    record.setFlowStepDesc(getFlowStep(record));
                    record.setCarType(RuleConditionConstant.IsLcvEnum.getNameByIndex(Integer.valueOf(record.getCarType())));
                    record.setAppCodeSuffix(getAppCodeSuffix(record));
                    record.setGpsCount(com.mljr.gps.common.util.StringUtils.killNull(record.getGpsCount()));
                    record.setFlowRemark(com.mljr.gps.common.util.StringUtils.killNull(record.getFlowRemark()));
                    record.setGpsDesc(AppInfoIsGpsEnum.getNameByIndex(record.getIsGps()));
                    if (customerNameMap != null) {
                        record.setCustomerName(customerNameMap.get(record.getAppCode()));
                    }
                }
            }
        } catch (Exception e) {
            log.error("{}异常,form={}",LOG_TITLE,JSON.toJSON(form),e);
            return Result.failInServer(PageVO.newInstance(totalCount,carGpsReList));
        }
        return Result.suc(PageVO.newInstance(totalCount,carGpsReList));
    }

上述代码只是几个接口业务逻辑处理的其中一个代码片段,其他接口跟这个接口大同小异。只是相关查询依赖的service接口不一样,数据转换逻辑有些差异,对于页面查询参数等处理有些差异以外,其他都是类似代码。

2.设计思路

引入设计模式,提高代码复用和扩展性。

  • 代理模式:包装对新旧接口的灰度控制切换(QueryListProxy)。
  • 适配器模式:解决新接口参数和返回结果对于老接口不兼容问题(RejectedQueryListHandler等以“Handler”结尾的类)。
  • 工厂模式:对于适配器类(以“Handler”结尾的类)的对象实例产生包装,客户端调用无需关注Handler具体如何产生(QueryListHandlerFactory)。
  • 模板方法:封装共同抽象逻辑骨架以及相关公用代码,交由子类实现差异细节(AbstractQueryListHandler)
2.1 UML图

在这里插入图片描述

2.1.1 QueryListContext

该类是一个泛型类,规约定义分页查询参数F以及分页查询结果V。其中成员变量DiamondConfig是个配置类(维护相关全局配置参数,包括新旧接口灰度开关),而PoseidonClient即新接口查询client类。

/**
 * @description: 查询列表上下文对象
 * <F> 封装查询参数Form
 * <V> 封装查询分页VO
 * @Date : 2019/5/24 上午11:08
 * @Author : 石冬冬-Seig Heil
 */
@Data
@NoArgsConstructor
@AllArgsConstructor
@Builder
public class QueryListContext<F extends Serializable,V extends Serializable> {
    /**
     * GPS审核流程Service
     */
    protected GpsFlowService gpsFlowService;
    /**
     * 查询门面
     */
    protected GpsQueryListFacade gpsQueryListFacade;
    /**
     * 服务调用client
     */
    protected PoseidonClient poseidonClient;
    /**
     * 分页查询Form对象
     */
    protected PageForm<F> pageForm;
    /**
     * 分页查询结果
     */
    protected PageVO<V> pageVo;
    /**
     * 配置
     */
    protected DiamondConfig config;
}
2.1.2 QueryListHandle

该类定义了模板方法相关抽象骨架方法,其中PageVo即负责最终各个适配器类内部新旧接口结果集的转换工作。

/**
 * @description: 查询列表 Handle
 * @Date : 2019/5/24 上午10:59
 * @Author : 石冬冬-Seig Heil
 */
public interface QueryListHandle<C extends QueryListContext,V extends Serializable>{
    /**
     * 处理查询参数
     * @param ctx
     */
    void prepare(C ctx);

    /**
     * 处理查询数据
     */
    void handle();

    /**
     * 数据加工
     */
    void mapping();

    /**
     * 后置处理
     */
    void after();

    /**
     * 查询结果集转换
     * @return
     */
    PageVO<V> view();
}
2.1.3 QueryFlowListHandle

该类的作用,对于几个查询列表,有几个需要特殊处理,但是子类又有相关共同的代码,因此提取的一个接口。其中,skipAppStatus()方法交由子类实现,以实现相关查询结果集需要进一步过滤筛选的状态过滤集合。

/**
 * @description: 对于GPS审批流程的数据处理接口
 * 适用于:GPS安装单已驳回、GPS安装单已上传、我的GPS领单
 * @Date : 2019/6/12 下午7:27
 * @Author : 石冬冬-Seig Heil
 */
public interface QueryFlowListHandle {
    /**
     * 构建查询Form参数
     * @return
     */
    GpsFlowForm buildQueryParam();
    /**
     * 设置VO域值
     * @param record
     * @param vo
     */
    void setFieldValues(GpsFlow record, GpsQueryListVo vo);
    /**
     * 要过滤的订单状态集合
     * {@link AppInfoStatusEnum#getIndex()}
     * @return
     */
    List<Integer> skipAppStatus();
}
2.1.4 QueryListHandlerFactory

Handler类(即实现各个查询接口的处理类)的对象实例产生,我们可以看到工厂方法规约了Class类一定要继承最上层抽象类AbstractQueryListHandler,防止客户端乱传参数。

/**
 * @description: GPS查询列表Handler Factory
 * @Date : 2019/5/29 下午3:40
 * @Author : 石冬冬-Seig Heil
 */
@Slf4j
public final class QueryListHandlerFactory {
    /**
     * 工厂方法
     * @param clazz
     * @param <T>
     * @return
     */
    public static  <T extends AbstractQueryListHandler> AbstractQueryListHandler create(Class<T> clazz){
        try {
            return (AbstractQueryListHandler)Class.forName(clazz.getName()).newInstance();
        } catch (Exception e) {
            log.error("create exception,name={}",clazz.getName(),e);
        }
        return null;
    }

    private QueryListHandlerFactory(){}
}
2.1.5 AbstractQueryListHandler

该类是个上层抽象类,并实现了QueryListHandle接口。同时该抽象类依然是个泛型类,并规约了查询参数F需要继承BaseForm类、查询结果V需要实现Serializable序列化接口。

/**
 * @description: 抽象GPS查询列表处理器
 * @Date : 2019/5/24 上午10:57
 * @Author : 石冬冬-Seig Heil
 */
@Slf4j
public abstract class AbstractQueryListHandler<F extends BaseForm,V extends Serializable> implements QueryListHandle<QueryListContext,V>{
    /**
     * 字符串分隔符
     */
    final String DELIM = ",";
    /**
     * 默认字符串数值
     */
    final String ZERO = "0";

    public AbstractQueryListHandler() {
    }

    /**
     * 构造函数
     * @param module
     */
    public AbstractQueryListHandler(String module) {
        this.module = module;
    }

    /**
     * 标示是否过滤当前分页集合中元素
     */
    protected boolean skipCurrentRecord;
    /**
     * 是否查询申请单销售、运营信息
     */
    protected boolean includeOperateInfo;
    /**
     * 流程状态
     */
    protected GpsFlowStatusEnum[] flowStatusEnums;
    /**********************************Mapping**********************************
    /**
     * GPS设备 Mapping
     * <单号,安装信息>
     */
    protected Map<String,List<CarGps>> gpsDeviceMapping = Collections.emptyMap();
    /**
     * 关联信息 Mapping
     * <单号,关联信息>
     */
    protected Map<String,SimpleAppRelationInfoRe> relationMapping = Collections.emptyMap();
    /**********************************Service**********************************
    /**
     * GPS审核流程Service
     */
    protected GpsFlowService gpsFlowService;
    /**
     * 上下文对象
     */
    protected QueryListContext<F,V> context;
    /**
     * 查询门面
     */
    protected GpsQueryListFacade gpsQueryListFacade;
    /**
     * 服务调用client
     */
    protected PoseidonClient poseidonClient;
    /**********************************查询相关**********************************
     /**
     * 模块名称
     */
    protected String module;
    /**
     * 查询条数
     */
    protected int totalCount;
    /**
     * 过滤申请单状态集合
     */
    protected List<Integer> skipStatusScope = Collections.emptyList();
    /**
     * 查询列表集合
     */
    protected List<GpsFlow> flowQueryList = Collections.emptyList();
    /**
     * 当前页面申请单号集合
     */
    protected List<String> appCodeScope = Collections.emptyList();
    /**
     * 分页查询Form对象
     */
    protected PageForm<F> pageForm;
    /**
     * 条件参数
     */
    protected F params;

    @Override
    public void prepare(QueryListContext ctx) {
        context = ctx;
        poseidonClient = ctx.poseidonClient;
        gpsFlowService = ctx.gpsFlowService;
        gpsQueryListFacade = ctx.gpsQueryListFacade;
        pageForm = ctx.pageForm;
        params = pageForm.getForm();
        if(StringTools.isNotEmpty(params.getBeginTime())){
            pageForm.getForm().setBeginTime(TimeTools.appendBeginOfDay(params.getBeginTime()));
        }
        if(StringTools.isNotEmpty(params.getEndTime())){
            pageForm.getForm().setEndTime(TimeTools.appendEndOfDay(params.getEndTime()));
        }
        log.info("{},form={}",module, JSONObject.toJSONString(params));
    }

    @Override
    public void mapping() {
        if(!appCodeScope.isEmpty()){
            AppRelationInfoDTO relationInfoDTO = AppRelationInfoDTO.builder().appCodeScope(appCodeScope)
                    .includingOperateInfo(includeOperateInfo)
                    .systemSource(poseidonClient.systemSource().name()).build();
            List<SimpleAppRelationInfoRe> relationInfoReList = poseidonClient.querySimpleAppRelationInfoList(relationInfoDTO);
            if(CollectionsTools.isNotEmpty(relationInfoReList)){
                relationMapping = relationInfoReList.stream().collect(Collectors.toMap(SimpleAppRelationInfoRe::getAppCode, Function.identity()));
            }
            gpsDeviceMapping = Optional.ofNullable(gpsQueryListFacade.getGpsDeviceListByAppCodes(appCodeScope)).orElse(Collections.emptyMap());
        }
    }

    /**
     * 执行
     */
    public final void execute(QueryListContext ctx){
        prepare(ctx);
        handle();
        mapping();
        after();
    }

    @Override
    public void after() {
        context.setPageVo(view());
    }

    /**
     * 查询退回的单号集合
     * @param appCodeScope
     * @return
     */
    List<String> getGpsIsBackListByAppCodes(List<String> appCodeScope){
        return gpsQueryListFacade.getGpsIsBackListByAppCodes(appCodeScope);
    }

    /**
     * 获取配置测试门店集合
     * @return
     */
    List<Integer> getTestDealers(){
        return gpsQueryListFacade.getTestDealers();
    }

    /**
     * 集合元素处理
     * @param origin
     * @param mapper
     * @param <E>
     * @param <R>
     * @return
     */
    <E,R> List<R> collects(Collection<E> origin, Function<? super E, ? extends R> mapper){
        return origin.stream().map(mapper).collect(toList()).stream().filter(each -> !StringUtils.isEmpty(each)).collect(toList());
    }

    /**
     * 从关联信息获取并设置VO对象中
     * @param appCode
     * @param vo
     */
    void setValueFromRelationInfo(String appCode,GpsQueryListVo vo,SimpleAppRelationInfoRe simpleAppRelationInfoRe){
        skipCurrentRecord = skipStatusScope.contains(Integer.valueOf(simpleAppRelationInfoRe.getStatus()));
        if(null != simpleAppRelationInfoRe && skipCurrentRecord){
            log.info("skip record appCode={},status={}",appCode,simpleAppRelationInfoRe.getStatus());
            totalCount --;
        }else{
            log.info("keep record appCode={},status={}",appCode,simpleAppRelationInfoRe.getStatus());
        }
        if(null != simpleAppRelationInfoRe){
            vo.setCustomerName(simpleAppRelationInfoRe.getCustomerName());
            vo.setCompanyName(simpleAppRelationInfoRe.getCompanyName());
            vo.setDealerName(simpleAppRelationInfoRe.getDealerName());
            vo.setAppStatus(Integer.valueOf(simpleAppRelationInfoRe.getStatus()));
            vo.setFlowStepDesc(getFlowStep(vo));
        }else{
            vo.setCustomerName("");
            vo.setCompanyName("");
            vo.setDealerName("");
            vo.setAppStatus(-1);
            vo.setFlowStepDesc("");
        }
    }

    /**
     * 获取流程阶段
     * @param record
     * @return
     */
    String getFlowStep(GpsQueryListVo record){
        int status = record.getAppStatus();
        boolean status_29 = AppInfoStatusEnum._29 == AppInfoStatusEnum.getByIndex(status);
        boolean status_19 = AppInfoStatusEnum._19 == AppInfoStatusEnum.getByIndex(status);
        boolean loanCondition = status_29 || status_19;
        CarGpsConstant.AppInfoIsGpsEnum appInfoIsGpsEnum = CarGpsConstant.AppInfoIsGpsEnum.getByIndex(Optional.ofNullable(record.getIsGps()).orElse(CarGpsConstant.AppInfoIsGpsEnum.UNINSTALL.getIndex()));
        int gpsCount = Integer.valueOf(Optional.ofNullable(record.getGpsCount()).orElse(ZERO));
        boolean gpsCondition = CarGpsConstant.AppInfoIsGpsEnum.INSTALLED != appInfoIsGpsEnum && gpsCount > 0;
        boolean flowSeq = (null != record.getFlowSeq() && 3 != record.getFlowSeq());
        String statusDesc = AppInfoStatusEnum.getNameByIndex(status);
        if(null != statusDesc){
            StringBuilder flowStep = new StringBuilder(AppInfoStatusEnum.getNameByIndex(status));
            if(flowSeq && loanCondition && gpsCondition){
                flowStep.append("(GPS待安装)");
            }
            return flowStep.toString();
        }
        return MessageFormat.format("UNKNOWN-[{0}]",status);
    }
}
2.1.6 AbstractQueryFlowListHandler

该类的作用,封装了几个查询接口相关共同代码,其中view方法实现即需要转换对应VO类。

/**
 * @description: 对于查询ca_gps_flow表的抽象封装
 * 适用于:GPS安装单已驳回、GPS安装单已上传、我的GPS领单
 * @Date : 2019/6/11 下午7:26
 * @Author : 石冬冬-Seig Heil
 */
@Slf4j
public abstract class AbstractQueryFlowListHandler extends AbstractQueryListHandler<GpsQueryListForm,GpsQueryListVo> implements QueryFlowListHandle{
    /**
     * 类型转换定义
     */
    final TypeReference<DiamondConfig.QueryListSkipStatusScopeConfig> TYPES = new TypeReference<DiamondConfig.QueryListSkipStatusScopeConfig>(){};
    /**
     * 前缀
     */
    protected final List<String> SUFFIX = Arrays.asList("退");
    /**
     * 测试门店集合
     */
    protected List<Integer> testDealerCodeScope = Collections.emptyList();
    /**
     * 状态过滤集合额
     */
    protected DiamondConfig.QueryListSkipStatusScopeConfig scopeConfig;

    /**
     * 构造函数
     * @param module 模块名称
     * @param flowStatusEnums 流程状态枚举
     */
    public AbstractQueryFlowListHandler(String module, GpsFlowStatusEnum[] flowStatusEnums) {
        super(module);
        this.flowStatusEnums = flowStatusEnums;
    }

    @Override
    public void prepare(QueryListContext ctx) {
        super.prepare(ctx);
        scopeConfig = ctx.config.of(ctx.config.queryListSkipStatusScope,TYPES);
        skipStatusScope = skipAppStatus();
        testDealerCodeScope = getTestDealers();
    }

    @Override
    public GpsFlowForm buildQueryParam() {
        GpsFlowForm flowForm = GpsFlowForm.builder().appCode(params.getAppCode()).customerName(params.getCustomerName()).build();
        if(null != flowStatusEnums && flowStatusEnums.length > 0){
            flowForm.setFlowStatusScope(Stream.of(flowStatusEnums).map(EnumValue::getIndex).collect(Collectors.toList()));
        }
        return flowForm;
    }

    @Override
    public void handle() {
        PageForm<GpsFlowForm> pageQueryForm = PageForm.newInstance(pageForm.getStart(),pageForm.getLimit(),buildQueryParam());
        totalCount = gpsFlowService.queryCount(pageQueryForm);
        if(totalCount != 0){
            flowQueryList = gpsFlowService.pageQuery(pageQueryForm);
            appCodeScope = collects(flowQueryList,GpsFlow::getAppCode);
        }
    }

    @Override
    public PageVO<GpsQueryListVo> view() {
        if(flowQueryList.size() == 0){
            return PageVO.newInstance(totalCount,Collections.emptyList());
        }
        List<GpsQueryListVo> voList = Lists.newArrayListWithExpectedSize(flowQueryList.size());
        //曾经被驳回的GPS审批单
        List<String> rejectAppCodes = getGpsIsBackListByAppCodes(appCodeScope);
        final List<Integer> skipStatusScope = skipAppStatus();
        log.info("module={},skipStatusScope={}",module,skipStatusScope.toArray());
        //vo转换
        GpsQueryListVo vo;
        for(GpsFlow record : flowQueryList ) {
            String appCode = record.getAppCode();
            vo = new GpsQueryListVo();
            SimpleAppRelationInfoRe simpleAppRelationInfoRe  = relationMapping.get(appCode);
            super.setValueFromRelationInfo(appCode,vo,simpleAppRelationInfoRe);
            if(skipCurrentRecord){
                continue;
            }
            List<CarGps> carGpsList = gpsDeviceMapping.getOrDefault(appCode,Collections.emptyList());
            List<String> gpsNoList = collects(carGpsList,CarGps::getGpsNo);
            List<String> auditSupplement = collects(carGpsList,CarGps::getAuditSupplement);
            List<String> autoAuditResult = collects(carGpsList,CarGps::getAutoAuditResult);
            List<String> manualAuditResult = collects(carGpsList,CarGps::getManualAuditResult);
            vo.setAppCode(record.getAppCode());
            vo.setGpsDeviceNo(StringTools.valueOfList(gpsNoList,DELIM));
            vo.setAuditSupplement(StringTools.valueOfList(auditSupplement,DELIM));
            vo.setAutoAuditResult(StringTools.valueOfList(autoAuditResult,DELIM));
            vo.setManualAuditResult(StringTools.valueOfList(manualAuditResult,DELIM));
            vo.setFlowStepDesc(getFlowStep(vo));
            vo.setAppCodeSuffix(rejectAppCodes.contains(record.getAppCode()) ? SUFFIX : Collections.emptyList());
            vo.setUpdateTime(record.getSubmitTime());
            if(null != record.getDealerCode()){
                vo.setDealerCode(String.valueOf(record.getDealerCode()));
            }
            setFieldValues(record,vo);
            voList.add(vo);
        }
        return PageVO.newInstance(totalCount,voList);
    }

    @Override
    public void setFieldValues(GpsFlow record, GpsQueryListVo vo) {

    }
}
2.1.7 AbstractQueryExportListHandler

该类的作用,对于几个查询导出业务场景处理的进一步抽象。

/**
 * @description: 查询数据导出抽象类
 * @Date : 2019/6/14 下午4:57
 * @Author : 石冬冬-Seig Heil
 */
@Slf4j
public abstract class AbstractQueryExportListHandler extends AbstractQueryListHandler<GpsCompositeQueryForm,GpsCompositeQuery> implements QueryFlowListHandle{
    /**
     * 类型转换定义
     */
    final TypeReference<DiamondConfig.QueryListSkipStatusScopeConfig> TYPES = new TypeReference<DiamondConfig.QueryListSkipStatusScopeConfig>(){};
    /**
     * 状态过滤集合额
     */
    protected DiamondConfig.QueryListSkipStatusScopeConfig scopeConfig;

    /**
     * 构造函数
     * @param module 模块名称
     * @param flowStatusEnums 流程状态枚举
     */
    public AbstractQueryExportListHandler(String module, GpsFlowStatusEnum[] flowStatusEnums) {
        super(module);
        this.flowStatusEnums = flowStatusEnums;
    }

    @Override
    public void prepare(QueryListContext ctx) {
        super.prepare(ctx);
        scopeConfig = ctx.config.of(ctx.config.queryListSkipStatusScope,TYPES);
        skipStatusScope = skipAppStatus();
        includeOperateInfo = true;
    }

    @Override
    public PageVO<GpsCompositeQuery> view() {
        if(flowQueryList.size() == 0){
            return PageVO.newInstance(totalCount,Collections.emptyList());
        }
        List<GpsQueryListVo> voList = Lists.newArrayListWithExpectedSize(flowQueryList.size());
        final List<Integer> skipStatusScope = skipAppStatus();
        log.info("module={},skipStatusScope={}",module,skipStatusScope.toArray());
        //vo转换
        GpsQueryListVo vo;
        for(GpsFlow record : flowQueryList) {
            String appCode = record.getAppCode();
            vo = new GpsQueryListVo();
            SimpleAppRelationInfoRe simpleAppRelationInfoRe  = relationMapping.get(appCode);
            super.setValueFromRelationInfo(appCode,vo,simpleAppRelationInfoRe);
            if(skipCurrentRecord){
                continue;
            }
            List<CarGps> carGpsList = gpsDeviceMapping.getOrDefault(appCode,Collections.emptyList());
            List<String> gpsNoList = collects(carGpsList,CarGps::getGpsNo);
            List<String> auditSupplement = collects(carGpsList,CarGps::getAuditSupplement);
            List<String> autoAuditResult = collects(carGpsList,CarGps::getAutoAuditResult);
            List<String> manualAuditResult = collects(carGpsList,CarGps::getManualAuditResult);
            List<String> wireDevices = carGpsList.stream().filter(each -> each.getGpsDealer().endsWith("YX")).map(CarGps::getGpsNo).collect(toList());
            List<CarGps> wirelessDevices = carGpsList.stream().filter(each -> each.getGpsDealer().endsWith("WX")).collect(toList());

            vo.setAppCode(record.getAppCode());
            vo.setGpsDeviceNo(StringTools.valueOfList(gpsNoList,DELIM));
            vo.setAuditSupplement(StringTools.valueOfList(auditSupplement,DELIM));
            vo.setAutoAuditResult(StringTools.valueOfList(autoAuditResult,DELIM));
            vo.setManualAuditResult(StringTools.valueOfList(manualAuditResult,DELIM));
            vo.setFlowStepDesc(getFlowStep(vo));
            vo.setFlowRemark(record.getRemark());
            vo.setAppCodeSuffix(Collections.emptyList());
            vo.setUpdateTime(record.getSubmitTime());
            vo.setAuditResult(GpsFlowStatusEnum.APPROVAL_SUCCESS.getIndex() == record.getFlowStatus() ? "审核成功" : "审批失败");
            vo.setProvince(simpleAppRelationInfoRe.getProvince());
            vo.setCarIdentify(simpleAppRelationInfoRe.getCarIdentify());
            vo.setSaleName(simpleAppRelationInfoRe.getSaleName());
            if(StringTools.isNotEmpty(record.getApprovalTime())){
                vo.setAuditDate(record.getApprovalTime().substring(0,10));
            }else{
                vo.setAuditDate("");
            }
            vo.setWireDeviceNo(StringTools.valueOfList(wireDevices,DELIM));
            List<Integer> wirelessInstallWay = collects(wirelessDevices,CarGps::getGpsInstallWay);
            vo.setWirelessInstallType(wirelessInstallWay.isEmpty() ? "" : CarGpsConstant.GpsInstallTypeEnum.getNameByIndex(wirelessInstallWay.get(0)));
            vo.setCarSeries(simpleAppRelationInfoRe.getCarSeries());
            vo.setCarColor(simpleAppRelationInfoRe.getCarColor());
            vo.setWirelessDeviceNo(StringTools.valueOfList(collects(wirelessDevices,CarGps::getGpsNo),DELIM));
            vo.setWirelessGpsPosition(StringTools.valueOfList(collects(wirelessDevices,CarGps::getGpsPosition),DELIM));
            vo.setLoanPeriods(simpleAppRelationInfoRe.getLoanPeriod());
            vo.setApprovalUserName(record.getApprovalUserName());

            setFieldValues(record,vo);
            voList.add(vo);
        }
        return PageVO.newInstance(totalCount,voList);
    }

    @Override
    public void setFieldValues(GpsFlow record, GpsQueryListVo vo) {

    }
}
2.1.8 流程类 RejectedQueryListHandler、InstalledQueryListHandler、MineLeadQueryListHandler

他们共同继承了AbstractQueryFlowListHandler。
GPS安装单已驳回,可见代码清晰简洁。

/**
 * @description: GPS安装单已驳回
 * @Date : 2019/5/24 上午11:04
 * @Author : 石冬冬-Seig Heil
 */
@Slf4j
public class RejectedQueryListHandler extends AbstractQueryFlowListHandler{

    public RejectedQueryListHandler() {
        super("queryListForRejectedGps", new GpsFlowStatusEnum[]{GpsFlowStatusEnum.REJECTED,GpsFlowStatusEnum.MASTER_BACK});
    }

    @Override
    public List<Integer> skipAppStatus() {
        return scopeConfig.rejectedList;
    }
}

GPS安装单已上传

/**
 * @description: GPS安装单已上传
 * @Date : 2019/5/25 下午6:15
 * @Author : 石冬冬-Seig Heil
 */
@Slf4j
public class InstalledQueryListHandler extends AbstractQueryFlowListHandler{


    public InstalledQueryListHandler() {
        super("queryListForInstalledGps",new GpsFlowStatusEnum[]{GpsFlowStatusEnum.PROCESSING});
    }

    @Override
    public GpsFlowForm buildQueryParam() {
        GpsFlowForm flowForm = super.buildQueryParam();
        if(null != params.getTest() && params.getTest().booleanValue()){
            flowForm.setDealerCodeScope(getTestDealers());
        }
        return flowForm;
    }

    @Override
    public void setFieldValues(GpsFlow record, GpsQueryListVo vo) {
        vo.setGpsFlowStep(record.getFlowStep());
        vo.setGpsFlowStepDesc(GpsFlowStepEnum.getNameByIndex(record.getFlowStep()));
        vo.setGpsFlowStatus(record.getFlowStatus());
        vo.setGpsFlowStatusDesc(GpsFlowStatusEnum.getNameByIndex(record.getFlowStatus()));
        vo.setApprovalUserName(record.getApprovalUserName());
        vo.setTestDealer(getTestDealers().contains(record.getDealerCode()));
    }

    @Override
    public List<Integer> skipAppStatus() {
        return scopeConfig.installedList;
    }
}

我的GPS领单

/**
 * @description: 我的GPS领单
 * @Date : 2019/5/29 上午11:45
 * @Author : 石冬冬-Seig Heil
 */
@Slf4j
public class MineLeadQueryListHandler extends AbstractQueryFlowListHandler{

    public MineLeadQueryListHandler() {
        super("queryListForMineGps",new GpsFlowStatusEnum[]{GpsFlowStatusEnum.PROCESSING});
    }

    @Override
    public GpsFlowForm buildQueryParam() {
        GpsFlowForm flowForm = super.buildQueryParam();
        flowForm.setApprovalUserName(params.getApprovalUserName());
        return flowForm;
    }

    @Override
    public List<Integer> skipAppStatus() {
        return scopeConfig.mineList;
    }
}
2.1.9 数据到类MineLeadExportQueryListHandler、GeneralQueryListExportHandler

他们共同继承了AbstractQueryExportListHandler。
我的GPS领单-数据导出

/**
 * @description: 我的GPS领单-数据导出
 * @Date : 2019/5/29 上午11:45
 * @Author : 石冬冬-Seig Heil
 */
@Slf4j
public class MineLeadExportQueryListHandler extends AbstractQueryExportListHandler{

    public MineLeadExportQueryListHandler() {
        super("queryListForMineLeadExport", new GpsFlowStatusEnum[]{GpsFlowStatusEnum.PROCESSING});
    }

    @Override
    public GpsFlowForm buildQueryParam() {
        GpsFlowForm flowForm = GpsFlowForm.builder().build();
        if(null != flowStatusEnums && flowStatusEnums.length > 0){
            flowForm.setFlowStatusScope(Stream.of(flowStatusEnums).map(EnumValue::getIndex).collect(Collectors.toList()));
        }
        flowForm.setApprovalUserName(params.getApprovalUserName());
        return flowForm;
    }

    @Override
    public void handle() {
        PageForm<GpsFlowForm> pageQueryForm = PageForm.newInstance(pageForm.getStart(),pageForm.getLimit(),buildQueryParam());
        totalCount = gpsFlowService.queryCount(pageQueryForm);
        if(totalCount != 0){
            flowQueryList = gpsFlowService.pageQuery(pageQueryForm);
            appCodeScope = collects(flowQueryList, GpsFlow::getAppCode);
        }
    }

    @Override
    public List<Integer> skipAppStatus() {
        return scopeConfig.mineList;
    }
}
/**
 * @description: GPS综合查询-数据导出
 * @Date : 2019/5/26 上午11:17
 * @Author : 石冬冬-Seig Heil
 */
@Slf4j
public class GeneralQueryListExportHandler extends AbstractQueryExportListHandler{

    final GpsFlowStatusEnum[] DEFAULT_STATUS = new GpsFlowStatusEnum[]{GpsFlowStatusEnum.APPROVAL_SUCCESS,GpsFlowStatusEnum.REJECTED,GpsFlowStatusEnum.PROCESSING,GpsFlowStatusEnum.MASTER_BACK};


    public GeneralQueryListExportHandler() {
        super("queryListForGeneralExport",new GpsFlowStatusEnum[]{GpsFlowStatusEnum.APPROVAL_SUCCESS,GpsFlowStatusEnum.REJECTED,GpsFlowStatusEnum.PROCESSING,GpsFlowStatusEnum.MASTER_BACK});
    }

    @Override
    public List<Integer> skipAppStatus() {
        return Collections.emptyList();
    }

    @Override
    public GpsFlowForm buildQueryParam() {
        String auditResult = Optional.ofNullable(params.getAuditResult()).orElse("-1");
        GpsFlowForm flowForm = GpsFlowForm.builder()
                .approvalUserName(params.getApprovalUserName())
                .flowStatusScope(Stream.of(DEFAULT_STATUS).map(EnumValue::getIndex).collect(Collectors.toList()))
                .build();
        switch (auditResult){
            //审核成功
            case "1":
                flowForm.setFlowStatusScope(Arrays.asList(GpsFlowStatusEnum.APPROVAL_SUCCESS.getIndex()));
                break;
            //审核失败
            case "2":
                flowForm.setFlowStatusScope(Arrays.asList(GpsFlowStatusEnum.REJECTED.getIndex()));
                break;
        }
        if(StringTools.isNotEmpty(params.getBeginTime())){
            flowForm.setBeginTime(TimeTools.appendBeginOfDay(params.getBeginTime()));
        }
        if(StringTools.isNotEmpty(params.getEndTime())){
            flowForm.setEndTime(TimeTools.appendEndOfDay(params.getEndTime()));
        }
        return flowForm;
    }

    @Override
    public void handle() {
        PageForm<GpsFlowForm> pageQueryForm = PageForm.newInstance(pageForm.getStart(),pageForm.getLimit(),buildQueryParam());
        totalCount = gpsFlowService.queryCount(pageQueryForm);
        if(totalCount != 0){
            flowQueryList = gpsFlowService.pageQuery(pageQueryForm);
            appCodeScope = collects(flowQueryList, GpsFlow::getAppCode);
        }
    }

}
2.1.10 通用类 GeneralQueryListHandler

他们共同继承了AbstractQueryListHandler。

/**
 * @description: GPS综合查询
 * @Date : 2019/5/25 下午6:15
 * @Author : 石冬冬-Seig Heil
 */
@Slf4j
public class GeneralQueryListHandler extends AbstractQueryListHandler<GpsQueryListForm,GpsQueryListVo>{

    protected List<GpsGeneralQueryRe> resultList;


    public GeneralQueryListHandler() {
        super("queryListForGpsGeneral");
    }

    /**
     * 构建查询参数
     * @return
     */
    GpsQueryListForm buildQueryParam() {
        GpsQueryListForm queryForm = GpsQueryListForm.builder()
                .appCode(params.getAppCode())
                .customerName(params.getCustomerName())
                .carIdentify(params.getCarIdentify())
                .build();
        return queryForm;
    }

    @Override
    public void handle() {
        GpsGeneralQueryDTO dto = new GpsGeneralQueryDTO();
        BeanUtils.copyProperties(buildQueryParam(),dto);
        resultList = poseidonClient.gpsGeneralQueryList(dto);
        totalCount = resultList.size();
    }


    @Override
    public PageVO<GpsQueryListVo> view() {
        if(resultList.size() == 0){
            return PageVO.newInstance(totalCount,Collections.emptyList());
        }
        List<GpsQueryListVo> voList = Lists.newArrayListWithExpectedSize(resultList.size());
        GpsQueryListVo vo;
        for(GpsGeneralQueryRe record : resultList ) {
            vo = new GpsQueryListVo();
            vo.setAppCode(record.getAppCode());
            vo.setCustomerName(record.getCustomerName());
            vo.setCompanyName(record.getCompanyName());
            vo.setDealerName(record.getDealerName());
            vo.setCarIdentify(record.getCarIdentify());
            vo.setCarSeries(record.getCarSeries());
            vo.setGpsDesc(CarGpsConstant.AppInfoIsGpsEnum.getNameByIndex(Integer.valueOf(record.getIsGps())));
            vo.setAppStatus(Integer.valueOf(record.getStatus()));
            vo.setFlowStepDesc(getFlowStep(vo));
            //冗余字段AppCodeSuffix,不给个空集合,前端页面无法正常显示页面。
            vo.setAppCodeSuffix(Collections.emptyList());
            voList.add(vo);
        }
        return PageVO.newInstance(totalCount,voList);
    }
}

GpsListForFengYunHandler

/**
 * @description: 对接风云系统-GPS安装列表
 * @Date : 2019/6/6 下午6:52
 * @Author : 石冬冬-Seig Heil
 */
@Slf4j
public class GpsListForFengYunHandler extends AbstractQueryListHandler<GpsQueryListForm,GpsInstalledListVo>{
    /**
     * 查询列表集合
     */
    protected List<GpsInstalledListVo> queryList = Collections.emptyList();

    /**
     * 构建查询DTO
     * @return
     */
    PageForm<GpsQueryListDTO> buildDTO(){
        GpsQueryListDTO dto = GpsQueryListDTO.builder()
                .appCode(params.getAppCode()).customerName(params.getCustomerName())
                .companyName(params.getCompanyName())
                .beginTime(params.getBeginTime()).endTime(params.getEndTime())
                .dealerCodeScope(params.getDealerCodeScope())
                .saleName(params.getSaleName()).operationName(params.getOperationName())
                .build();
        return PageForm.newInstance(pageForm.getStart(),pageForm.getLimit(),dto);
    }

    @Override
    public void handle() {
        Result<PageVO<GpsInstalledListVo>> result = poseidonClient.queryListForFengYun(buildDTO());
        if(result.isSuccess() && CollectionsTools.isNotEmpty(result.getData().getData())) {
            totalCount = result.getData().getRecordsTotal();
            queryList = result.getData().getData();
        }
    }

    @Override
    public PageVO<GpsInstalledListVo> view() {
        if (!queryList.isEmpty()) {
            //2、设置相关属性
            queryList.forEach(record -> {
                String appCode = record.getAppCode();
                List<CarGps> carGpsList = gpsDeviceMapping.getOrDefault(appCode, new ArrayList<>());
                List<String> autoAuditResult = collects(carGpsList,CarGps::getAutoAuditResult);
                List<String> manualAuditResult = collects(carGpsList,CarGps::getManualAuditResult);
                record.setAutoAuditResult(StringUtils.collectionToDelimitedString(autoAuditResult, DELIM));
                record.setManualAuditResult(StringUtils.collectionToDelimitedString(manualAuditResult, DELIM));
                record.setGpsCount(com.mljr.gps.common.util.StringUtils.killNull(record.getGpsCount()));
                record.setFlowRemark(com.mljr.gps.common.util.StringUtils.killNull(record.getFlowRemark()));
                record.setSaleName(com.mljr.gps.common.util.StringUtils.killNull(record.getSaleName()));
                record.setOperationName(com.mljr.gps.common.util.StringUtils.killNull(record.getOperationName()));
                record.setAppStatusDesc(AppInfoStatusEnum.getNameByIndex(record.getAppStatus()));
            });
        }
        return PageVO.newInstance(totalCount,queryList);
    }
}

2.1.11 代理类 QueryListProxy

具体作用详见类说明

/**
 * @description: GPS查询列表代理类
 * 该类的作用:
 * (1)、对于客户端,无需关注底层是如何控制新接口和老接口的切换逻辑,把交互细节委托给代理类。
 * (2)、该类通过xdiamond配置中心维护一个JSON控制各个接口开关逻辑。
 * {@link DiamondConfig#callPoseidonQueryList}
 * {@link com.mljr.gps.common.config.DiamondConfig.CallPoseidonQueryListEnable}
 * (3)、代理新接口交互调用。{@link PoseidonClient}
 * (4)、代理数据导出老接口调用,{@link GpsCompositeQueryFacade} 以及其他相关查询列表老接口调用。{@link GpsQueryListFacade}
 * (5)、对于GPS安装单已驳回、已上传、我的领单 则通过ca_gps_flow通过flow_status等相关条件过滤。
 * {@link com.mljr.gps.engine.handler.AbstractQueryFlowListHandler}
 * (6)、风云系统-GPS列表,查看
 * {@link GpsListForFengYunHandler} {@link QueryListProxy#queryListForFengYun(PageForm)}
 * @Date : 2019/5/23 下午12:17
 * @Author : 石冬冬-Seig Heil
 */
@Component
@Slf4j
public class QueryListProxy {

    @Autowired
    GpsFlowService gpsFlowService;

    @Autowired
    GpsQueryListFacade gpsQueryListFacade;

    @Autowired
    GpsCompositeQueryFacade gpsCompositeQueryFacade;

    @Autowired
    PoseidonClient poseidonClient;

    @Autowired
    DiamondConfig diamondConfig;

    /**
     * 车贷审批管理-GPS安装单已驳回
     * @param pageForm
     * @return
     */
    public Result<PageVO<GpsQueryListVo>> queryListForRejectedGps(PageForm<GpsQueryListForm> pageForm) {
        boolean enable = diamondConfig.of(diamondConfig.callPoseidonQueryList,new TypeReference<DiamondConfig.CallPoseidonQueryListEnable>(){}).queryListForRejectedGps;
        if(!enable){
            return gpsQueryListFacade.queryListForUnInstalledGps(pageForm);
        }
        AbstractQueryListHandler handler = QueryListHandlerFactory.create(RejectedQueryListHandler.class);
        QueryListContext<GpsQueryListForm,GpsQueryListVo> context = buildContext(pageForm);
        handler.execute(context);
        return Result.suc(context.getPageVo());
    }

    /**
     * 车贷审批管理-GPS安装单已上传
     * @param pageForm
     * @return
     */
    public Result<PageVO<GpsQueryListVo>> queryListForInstalledGps(PageForm<GpsQueryListForm> pageForm) {
        boolean enable = diamondConfig.of(diamondConfig.callPoseidonQueryList,new TypeReference<DiamondConfig.CallPoseidonQueryListEnable>(){}).queryListForInstalledGps;
        if(!enable){
            return gpsQueryListFacade.queryListForInstalledGps(pageForm);
        }
        AbstractQueryListHandler handler = QueryListHandlerFactory.create(InstalledQueryListHandler.class);
        QueryListContext<GpsQueryListForm,GpsQueryListVo> context = buildContext(pageForm);
        handler.execute(context);
        return Result.suc(context.getPageVo());
    }


    /**
     * 车贷审批管理-我的领单
     * @param pageForm
     * @return
     */
    public Result<PageVO<GpsQueryListVo>> queryListForMineGps(PageForm<GpsQueryListForm> pageForm) {
        boolean enable = diamondConfig.of(diamondConfig.callPoseidonQueryList,new TypeReference<DiamondConfig.CallPoseidonQueryListEnable>(){}).queryListForGpsApproveMine;
        if(!enable){
            return gpsQueryListFacade.queryListForGpsApproveMine(pageForm);
        }
        AbstractQueryListHandler handler = QueryListHandlerFactory.create(MineLeadQueryListHandler.class);
        pageForm.getForm().setApprovalUserName(AccessToken.get().getUserName());
        QueryListContext<GpsQueryListForm,GpsQueryListVo> context = buildContext(pageForm);
        handler.execute(context);
        return Result.suc(context.getPageVo());
    }

    /**
     * 我的gps领单-数据导出
     * @param pageForm
     * @return
     */
    public Result<PageVO<GpsCompositeQuery>> mineApprExportQuery(PageForm<GpsCompositeQueryForm> pageForm){
        boolean enable = diamondConfig.of(diamondConfig.callPoseidonQueryList,new TypeReference<DiamondConfig.CallPoseidonQueryListEnable>(){}).queryListForGpsApproveMineExport;
        if(!enable){
            return gpsCompositeQueryFacade.mineApprExportQuery(pageForm);
        }
        AbstractQueryListHandler handler = QueryListHandlerFactory.create(MineLeadExportQueryListHandler.class);
        pageForm.getForm().setApprovalUserName(AccessToken.get().getUserName());
        QueryListContext<GpsCompositeQueryForm,GpsCompositeQuery> context = buildContextForExport(pageForm);
        handler.execute(context);
        return Result.suc(context.getPageVo());
    }

    /**
     * GPS综合查询-列表查询
     * @param pageForm
     * @return
     */
    public Result<PageVO<GpsQueryListVo>> queryListForGpsGeneral(PageForm<GpsQueryListForm> pageForm){
        boolean enable = diamondConfig.of(diamondConfig.callPoseidonQueryList,new TypeReference<DiamondConfig.CallPoseidonQueryListEnable>(){}).queryListForGpsGeneral;
        if(!enable){
            return gpsQueryListFacade.queryListForGpsGeneral(pageForm);
        }
        AbstractQueryListHandler handler = QueryListHandlerFactory.create(GeneralQueryListHandler.class);
        handler.execute(buildContext(pageForm));
        return Result.suc(handler.view());
    }

    /**
     * GPS综合查询-数据导出
     * @param pageForm
     * @return
     */
    public Result<PageVO<GpsCompositeQuery>> queryListForGpsGeneralExport(PageForm<GpsCompositeQueryForm> pageForm){
        boolean enable = diamondConfig.of(diamondConfig.callPoseidonQueryList,new TypeReference<DiamondConfig.CallPoseidonQueryListEnable>(){}).queryListForGpsGeneralExport;
        if(!enable){
            return gpsCompositeQueryFacade.query(pageForm);
        }
        AbstractQueryListHandler handler = QueryListHandlerFactory.create(GeneralQueryListExportHandler.class);
        handler.execute(buildContextForExport(pageForm));
        return Result.suc(handler.view());
    }

    /**
     * 风云系统调用-GPS安装单列表
     * @param queryForm
     * @return
     */
    public Result<PageVO<GpsInstalledListVo>> queryListForFengYun(PageForm<GpsQueryListDTO> queryForm) {
        boolean enable = diamondConfig.of(diamondConfig.callPoseidonQueryList,new TypeReference<DiamondConfig.CallPoseidonQueryListEnable>(){}).queryGpsListForFengYun;
        if(!enable){
            return gpsQueryListFacade.queryListForInstalled(queryForm);
        }
        GpsQueryListDTO queryListDTO = queryForm.getForm();
        GpsQueryListForm queryListForm = GpsQueryListForm.builder()
                .appCode(queryListDTO.getAppCode()).customerName(queryListDTO.getCustomerName())
                .companyName(queryListDTO.getCompanyName())
                .appTimeStart(queryListDTO.getBeginTime()).appTimeEnd(queryListDTO.getEndTime())
                .dealerCodeScope(queryListDTO.getDealerCodeScope())
                .saleName(queryListDTO.getSaleName()).operationName(queryListDTO.getOperationName()).build();
        PageForm<GpsQueryListForm> pageForm = PageForm.newInstance(queryForm.getStart(),queryForm.getLimit(),queryListForm);
        GpsListForFengYunHandler handler = new GpsListForFengYunHandler();
        QueryListContext<GpsQueryListForm,GpsInstalledListVo> context = QueryListContext.<GpsQueryListForm,GpsInstalledListVo>builder()
                .gpsQueryListFacade(gpsQueryListFacade).poseidonClient(poseidonClient)
                .gpsFlowService(gpsFlowService).pageForm(pageForm).build();
        handler.execute(context);
        return Result.suc(context.getPageVo());
    }
    /**
     * 构建上下文
     * @param pageForm
     * @return
     */
    QueryListContext<GpsQueryListForm,GpsQueryListVo> buildContext(PageForm<GpsQueryListForm> pageForm){
        QueryListContext<GpsQueryListForm,GpsQueryListVo> queryListContext = QueryListContext.<GpsQueryListForm,GpsQueryListVo>builder()
                .gpsQueryListFacade(gpsQueryListFacade).poseidonClient(poseidonClient)
                .config(diamondConfig)
                .gpsFlowService(gpsFlowService).pageForm(pageForm).build();
        return queryListContext;
    }

    /**
     * 构建上下文
     * 适用业务场景:数据导出(譬如 我的领单、GPS综合查询)
     * @param pageForm
     * @return
     */
    QueryListContext<GpsCompositeQueryForm,GpsCompositeQuery> buildContextForExport(PageForm<GpsCompositeQueryForm> pageForm){
        QueryListContext<GpsCompositeQueryForm,GpsCompositeQuery> queryListContext = QueryListContext.<GpsCompositeQueryForm,GpsCompositeQuery>builder()
                .gpsQueryListFacade(gpsQueryListFacade).poseidonClient(poseidonClient)
                .config(diamondConfig)
                .gpsFlowService(gpsFlowService).pageForm(pageForm).build();
        return queryListContext;
    }
}

3. 综述总结

重构是个比较类的活,因此你的设计思路决定你重构的成本以及决定对现有代码的影响,是兼容,是适配,还是大量的各种调用方各种if判断,但是如果经过深思熟虑,并引入相关设计模式综合运用,就能够巧妙的发挥设计模式的作用意义。而设计模式又不是孤立存在的,因此会各种组合使用,发挥各自的优势,同时弥补各自的缺点。这样,我们最终才能写出称心如意的代码,容易对于后期扩展也奠定了基础。

下面的是我的公众号二维码图片,欢迎关注,或公众号搜索【秋夜无霜】。
秋夜无霜

  • 2
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值