1、ES6.X 新类型Join 产生背景

  • Mysql中多表关联,我们可以通过left join 或者Join等实现;

  • ES5.X版本,借助父子文档实现多表关联,类似数据库中Join的功能;实现的核心是借助于ES5.X支持1个索引(index)下多个类型(type)。

  • ES6.X版本,由于每个索引下面只支持单一的类型(type)。

  • 所以,ES6.X版本如何实现Join成为大家关注的问题。

幸好,ES6.X新推出了Join类型,主要解决类似Mysql中多表关联的问题。

2、ES6.X Join类型介绍

仍然是一个索引下,借助父子关系,实现类似Mysql中多表关联的操作。

3、ES6.X Join类型实战

3.1 ES6.X Join类型 Mapping定义

Join类型的Mapping如下:

核心 
- 1) “my_join_field”为join的名称。

  • 2)”question”: “answer” 指:qustion为answer的父类。
PUT my_join_index
{"mappings": {"_doc": {"properties": {"my_join_field": { "type": "join","relations": {"question": "answer" }}}}}
}

3.2 ES6.X join类型定义父文档

直接上以下简化的形式,更好理解些。

如下,定义了两篇父文档。 
文档类型为父类型:”question”。

PUT my_join_index/_doc/1?refresh
{"text": "This is a question","my_join_field": "question"
}PUT my_join_index/_doc/2?refresh
{"text": "This is another question","my_join_field": "question"
}

3.3 ES6.X join类型定义子文档

  • 路由值是强制性的,因为父文件和子文件必须在相同的分片上建立索引。
  • “answer”是此子文档的加入名称。
  • 指定此子文档的父文档ID:1。
PUT my_join_index/_doc/3?routing=1&refresh
{"text": "This is an answer","my_join_field": {"name": "answer", "parent": "1" }
}PUT my_join_index/_doc/4?routing=1&refresh
{"text": "This is another answer","my_join_field": {"name": "answer","parent": "1"}
}

4、ES6.X Join类型约束

  1. 每个索引只允许一个Join类型Mapping定义;
  2. 父文档和子文档必须在同一个分片上编入索引;这意味着,当进行删除、更新、查找子文档时候需要提供相同的路由值。
  3. 一个文档可以有多个子文档,但只能有一个父文档。
  4. 可以为已经存在的Join类型添加新的关系。
  5. 当一个文档已经成为父文档后,可以为该文档添加子文档。

5、ES6.X Join类型检索与聚合

5.1 ES6.X Join全量检索

GET my_join_index/_search
{"query": {"match_all": {}},"sort": ["_id"]
}

返回结果如下:

{"took": 1,"timed_out": false,"_shards": {"total": 5,"successful": 5,"skipped": 0,"failed": 0},"hits": {"total": 4,"max_score": null,"hits": [{"_index": "my_join_index","_type": "_doc","_id": "1","_score": null,"_source": {"text": "This is a question","my_join_field": "question"},"sort": ["1"]},{"_index": "my_join_index","_type": "_doc","_id": "2","_score": null,"_source": {"text": "This is another question","my_join_field": "question"},"sort": ["2"]},{"_index": "my_join_index","_type": "_doc","_id": "3","_score": null,"_routing": "1","_source": {"text": "This is an answer","my_join_field": {"name": "answer","parent": "1"}},"sort": ["3"]},{"_index": "my_join_index","_type": "_doc","_id": "4","_score": null,"_routing": "1","_source": {"text": "This is another answer","my_join_field": {"name": "answer","parent": "1"}},"sort": ["4"]}]}
}

5.2 ES6.X 基于父文档查找子文档

GET my_join_index/_search
{"query": {"has_parent" : {"parent_type" : "question","query" : {"match" : {"text" : "This is"}}}}
}

返回结果:

{"took": 0,"timed_out": false,"_shards": {"total": 5,"successful": 5,"skipped": 0,"failed": 0},"hits": {"total": 2,"max_score": 1,"hits": [{"_index": "my_join_index","_type": "_doc","_id": "3","_score": 1,"_routing": "1","_source": {"text": "This is an answer","my_join_field": {"name": "answer","parent": "1"}}},{"_index": "my_join_index","_type": "_doc","_id": "4","_score": 1,"_routing": "1","_source": {"text": "This is another answer","my_join_field": {"name": "answer","parent": "1"}}}]}
}

5.3 ES6.X 基于子文档查找父文档

GET my_join_index/_search
{
"query": {"has_child" : {"type" : "answer","query" : {"match" : {"text" : "This is question"}}}}
}

返回结果:

{"took": 0,"timed_out": false,"_shards": {"total": 5,"successful": 5,"skipped": 0,"failed": 0},"hits": {"total": 1,"max_score": 1,"hits": [{"_index": "my_join_index","_type": "_doc","_id": "1","_score": 1,"_source": {"text": "This is a question","my_join_field": "question"}}]}
}

5.4 ES6.X Join聚合操作实战

以下操作含义如下:

  • 1)parent_id是特定的检索方式,用于检索属于特定父文档id=1的,子文档类型为answer的文档的个数。
  • 2)基于父文档类型question进行聚合;
  • 3)基于指定的field处理。
GET my_join_index/_search
{"query": {"parent_id": { "type": "answer","id": "1"}},"aggs": {"parents": {"terms": {"field": "my_join_field#question", "size": 10}}},"script_fields": {"parent": {"script": {"source": "doc['my_join_field#question']" }}}
}

返回结果:

{"took": 1,"timed_out": false,"_shards": {"total": 5,"successful": 5,"skipped": 0,"failed": 0},"hits": {"total": 2,"max_score": 0.13353139,"hits": [{"_index": "my_join_index","_type": "_doc","_id": "3","_score": 0.13353139,"_routing": "1","fields": {"parent": ["1"]}},{"_index": "my_join_index","_type": "_doc","_id": "4","_score": 0.13353139,"_routing": "1","fields": {"parent": ["1"]}}]},"aggregations": {"parents": {"doc_count_error_upper_bound": 0,"sum_other_doc_count": 0,"buckets": [{"key": "1","doc_count": 2}]}}
}

6、ES6.X Join 一对多实战

6.1 一对多定义

如下,一个父文档question与多个子文档answer,comment的映射定义。

PUT join_ext_index
{"mappings": {"_doc": {"properties": {"my_join_field": {"type": "join","relations": {"question": ["answer", "comment"]  }}}}}
}

6.2 一对多对多定义

实现如下图的祖孙三代关联关系的定义。

question/    \/      \
comment  answer||vote
PUT join_multi_index
{"mappings": {"_doc": {"properties": {"my_join_field": {"type": "join","relations": {"question": ["answer", "comment"],  "answer": "vote" }}}}}
}

孙子文档导入数据,如下所示:

PUT join_multi_index/_doc/3?routing=1&refresh
{"text": "This is a vote","my_join_field": {"name": "vote","parent": "2" }
}

注意:

- 孙子文档所在分片必须与其父母和祖父母相同
- 孙子文档的父代号(必须指向其父亲answer文档)

7、小结

虽然ES官方文档已经很详细了,详见: 
http://t.cn/RnBBLgp

Elasticsearch6.X 新类型Join深入详解相关推荐

  1. java lambda表达式详解_Java8新特性Lambda表达式详解

    课程目标: 通过本课程的学习,详细掌握Java8新特性之Lambda表达式: 适用人群:有Java基础的开发人员: 课程概述:从Java 8出现以来lambda是最重要的特性之一,它可以让我们用简洁流 ...

  2. 【java8新特性】——Optional详解(三)

    一.简介 Optional类是Java8为了解决null值判断问题,借鉴google guava类库的Optional类而引入的一个同名Optional类,使用Optional类可以避免显式的null ...

  3. FreeEIM 来点新知识iOS UIScrollView详解

     老程序员FreeEIM 来点新知识iOS UIScrollView详解 UIScrollView 顾名思义也知道这个是和滚动相关的控件,在Android开发时遇到过ScrollView,当内容的 ...

  4. Java 11中的新功能和API详解系列1

    Java 11中的新功能和API详解系列1 2018.9.27 版权声明:本文为博主chszs的原创文章,未经博主允许不得转载. JDK 11在语言语法方面有一个小改动,增加了相当数量的新API,以及 ...

  5. Elasticsearch中字段类型(Field Type)详解

    ElasticSearch 7.7 字段类型(Field datatype)详解 字符串, object, 数值, 日期, 数组, 0x00 字符串: text, keyword 5.0以后,stri ...

  6. H5的新特性及API详解(很惊人)

    H5的新特性及API详解(很惊人) 2017-01-20 17:00 4057人阅读 评论(0) 收藏 举报  分类: h5(11)  js函数(64)  js技巧(15)  版权声明:本文为博主原创 ...

  7. java enum类默认常量是什么_Java枚举类型enum的详解及使用

    Java枚举类型enum的详解及使用 最近跟同事讨论问题的时候,突然同事提到我们为什么Java 中定义的常量值不采用enmu 枚举类型,而采用public final static 类型来定义呢?以前 ...

  8. pandas新字段(数据列)生成、使用np.where或者apply lambda函数结合if else生成新的字段,详解及实战

    pandas新字段(数据列)生成.使用np.where或者apply lambda函数结合if else生成新的字段,详解及实战 pandas apply用法: pandas apply方法的作用原理 ...

  9. java多线程中的join方法详解

    java多线程中的join方法详解 方法Join是干啥用的? 简单回答,同步,如何同步? 怎么实现的? 下面将逐个回答. 自从接触Java多线程,一直对Join理解不了.JDK是这样说的:join p ...

最新文章

  1. OPPO Find X3通过网站推广正式官宣,打破常规探索高端旗舰新突破!
  2. Web Deployment Projects with Visual Studio 2005
  3. SAP UI5 global configuration interface
  4. SSM三大框架超详细总结(适合你重新回顾)
  5. 解决 mklink 使用中的各种坑(硬链接,软链接/符号链接,目录链接)
  6. Linux网络编程--tcp服务器
  7. Master of Typing - Tutor for Mac(打字大师—盲打练习课程)
  8. 基于VS快速排序的单元测试
  9. Docker使用过程中经常遇见的问题
  10. 能力与知识、技能三者之间的区别与联系是什么?
  11. 一键调用API,聚合数据API服务助力企业应用创新
  12. 微信公众号接口类(PHP版本)
  13. 85款中国风字体!超级好看的古风系列
  14. 山东大学计算机组成与设计实验七 节拍脉冲发生器时序电路
  15. 基恩士XG-XvisionEditor修改程序ID号
  16. 在线测试视频地址(flv,m3u8,rtsp)
  17. 自己动手利用CentOS6.5 搭建php环境安装discuz论坛
  18. 没有SOA,CIO 将面临什么
  19. html5手指测速,网速html5网速测试进度条代码
  20. 波数及波数向量(波矢量)

热门文章

  1. python opencv图片放大 缩小_Python OpenCV之图片缩放的实现(cv2.resize)
  2. ie浏览器跳转谷歌浏览器_微软IE浏览器的命运:加速死亡
  3. OpenStack(一)——OpenStack与云计算概述
  4. scrapy框架_入门Scrapy框架看这一篇文章就够了
  5. python笔记之文件的基本操作和os模块
  6. php上传图片完成后的截图,php实现粘贴截图并完成上传功能
  7. 古风登陆html,再祭古风扬 文/凌霄一羽
  8. java web sqlmapapi,深入了解SQLMAP API
  9. alv 刷新_钜献 | 60小时刷新你的雅思托福成绩!明早9点我们要搞事情了!
  10. 微软服务器收费吗,了解 Azure 外部服务收费