最近来了新公司,主要用到了ElasitcSearch,大家都知道在底层查询代码中往往需要判断传入某个参数是否为空来判断设置查询,例如下方代码:

BoolQueryBuilder query = QueryBuilders.boolQuery();
if (param.getMusicId() != null) {
query.must(QueryBuilders.termQuery("musicId", keyword));
}
if (param.getMusicName() != null) {
query.must(QueryBuilders.matchQuery("musicName", keyword));
}
if (param.getTags() != null) {
query.must(QueryBuilders.termsQuery("tag", tags));
}
//..... 就这样N多if

以上情况一出现后,就导致了下次其他通知开发相关功能的时候,可能不符合他要求,他就会重新拷贝一份,然后再增加或者删除冗余一份出来满足自己需求,久而久之就 臃肿 了起来

于是乎我想到了学习的设计模式 策略模式 又想到了 Java8 Function ,当Function仅支持一个入参,于是我搜了下还有个BiFunction支持两个入参,

我打算将字段定义为策略Key,值就是Function,将查询构建代码抽离主逻辑,不多BB,直接上代码:

private static Map<MusicFieldEnum, BiFunction<BoolQueryBuilder, Object, QueryBuilder>> fieldQueryFunMap;

static {
fieldQueryFunMap = new HashMap<>();
fieldQueryFunMap.put(SHEET, (builder, value) -> builder.filter(QueryBuilders.termsQuery(SHEET.getCode(), value)));
fieldQueryFunMap.put(STATUS, (builder, value) -> builder.filter(QueryBuilders.termQuery(STATUS.getCode(), value)));
fieldQueryFunMap.put(MUSIC_ID, (builder, value) -> builder.filter(QueryBuilders.termsQuery(MUSIC_ID.getCode(), value)));
fieldQueryFunMap.put(SYS_TAG, (builder, value) -> builder.filter(QueryBuilders.nestedQuery(SYS_TAG.getCode(),QueryBuilders.termsQuery(SYS_TAG_ID.getCode(), value), ScoreMode.None)));
} public BoolQueryBuilder getQuery(Param param){
if (CollectionUtils.isEmpty(param.getSheetId())) {
fieldQueryFunMap.get(SHEET).apply(query, param.getSheetId());
}
if (CollectionUtils.isEmpty(param.getTags())) {
fieldQueryFunMap.get(SYS_TAG).apply(query, param.getTags());
}
if (param.getStatus() == ElasticsearchMusicStatuEnum.PUBLISH) {
fieldQueryFunMap.get(STATUS).apply(query, StatusEnum.PUBLISH_SUCCESS.code);
}
}

虽然代码量增加了点点,但我所想要达到的目的就是将字段的查询方式建立一个围栏,达到规范和便于重用。

使用Java8 的Function将查询构建代码单独抽离出来搭配策略模式,便于统一修改,也可以灵活装配,如有做的不当的地方大佬请赐教。

Java8 BiFunction 简单用用的更多相关文章

  1. Java8内置的函数式编程接口应用场景和方式

    首先,我们先定义一个函数式编程接口 @FunctionalInterface public interface BooleanFunctionalInterface<T> { boolea ...

  2. loadrunner 的Administration Page页面设置

    工作中用到Loadrunner不是很多,能够简单用用,深入的知识还得靠自己空余时自学.对于loadrunner 的Administration Page页面设置,我的理解是给自己设置各种障碍,然后一个 ...

  3. javascript组件化(转)

    javascript组件化(转) By purplebamboo 3月 16 2015 更新日期:3月 23 2015 文章目录 1. 最简陋的写法 2. 作用域隔离 3. 面向对象 4. 抽象出ba ...

  4. (转)javascript组件开发方式

    作为一名前端工程师,写组件的能力至关重要.虽然javascript经常被人嘲笑是个小玩具,但是在一代代大牛的前仆后继的努力下,渐渐的也摸索了一套组件的编写方式. 下面我们来谈谈,在现有的知识体系下,如 ...

  5. ssh优缺点

    面试归来 技术面试官叫我谈谈 ssh优缺点 平时用起来倒是挺顺手..但是从来没有系统的总结过..导致很多点会都没有说出来.. 这次我认真总结了一下... 常说的好处 开源 常说的坏处 配置文件过大我就 ...

  6. [转]nodejs日期时间插件moment.js

    本文转自:https://blog.csdn.net/dreamer2020/article/details/52278478 问题来源js自带的日期Date可以满足一些基本的需求,例如格式化.时间戳 ...

  7. 带着新人学springboot的应用12(springboot+Dubbo+Zookeeper 下)

    上半节已经下载好了Zookeeper,以及新建了两个应用provider和consumer,这一节我们就结合dubbo来测试一下分布式可不可以用. 现在就来简单用一下,注意:这里只是涉及最简单的部分, ...

  8. 前端js面向对象编程以及封装组件的思想

    demo-richbase 用来演示怎么使用richbase来制作组件的例子 作为一名前端工程师,写组件的能力至关重要.虽然javascript经常被人嘲笑是个小玩具,但是在一代代大牛的前仆后继的努力 ...

  9. 个人对JS原型链的一些理解(prototype、__proto__)

    前言 在我一开始学习java web的时候,对JS就一直抱着一种只是简单用用的心态,于是并没有一步一步地去学习,当时认为用法与java类似,但是在实际web项目中使用时却比较麻烦,便直接粗略了解后开始 ...

随机推荐

  1. 1.ASP.NET Core 管道、中间件、依赖注入

    自定义中间件(基于工厂) 自定义中间件(注入到第三方容器)

  2. Ubuntu——常用命令

    一.进入文件夹 1.cd .. # 进入上一个文件夹 2.cd ../.. # 进入上两个文件夹 3.cd - # 去到进入当前文件夹之前的那个文件夹 二.复制文件 cp 目标文件 复制文件名 三.移 ...

  3. Linux命令学习-01——find -type

    Linux find 命令用来在指定目录下查找文件. 任何位于参数之前的字符串都将被视为欲查找的目录名.如果使用该命令时,不设置任何参数,则 find 命令将在当前目录下查找子目录与文件.并且将查找到 ...

  4. linux 基础正则表达式练习

    感谢鸟哥!!! 如果Linux能够直接连网络,使用以下命令还获取文件吧 wget http://linux.vbird.org/linux_basic/0330regularex/regular_ex ...

  5. 【DP】区间DP入门

    在开始之前我要感谢y总,是他精彩的讲解才让我对区间DP有较深的认识. 简介 一般是线性结构上的对区间进行求解最值,计数的动态规划.大致思路是枚举断点,然后对断点两边求取最优解,然后进行合并从而得解. ...

  6. CSS字体大小: em与px、pt、百分比之间的对比

      CSS样式最混乱的一个方面是应用程序中文本扩展的font-size属性.在CSS中,你可以用四个不同的单位度量来显示在web浏览器中的文本大小.这四个单位哪一种最适合Web? 这个问题引起了广泛的 ...

  7. SVG in Action

    SVG in Action HTML5 semantic HTML5 Semantic Elements / HTML5 Semantic Tags figure object <figure& ...

  8. Promise.allSettled & Promise.all & Promise.race & Promise.any All In One

    Promise.allSettled & Promise.all & Promise.race & Promise.any All In One new Promise(), ...

  9. W3Schools Quizzes

    W3Schools Quizzes Test your skills https://www.w3schools.com/quiztest/default.asp Quiz HOME Quiz HTM ...

  10. 微信小程序 TypeScript bug

    微信小程序 TypeScript bug 执行自定义预览前预处理命令失败! internal/modules/cjs/loader.js:584 throw err; ^ Error: Cannot ...