Elasticsearch由浅入深(一)
什么是Elasticsearch
什么是搜索
百度:我们比如说想找寻任何的信息的时候,就会上百度去搜索一下,比如说找一部自己喜欢的电影,或者说找一本喜欢的书,或者找一条感兴趣的新闻(提到搜索的第一印象),百度 != 搜索
垂直搜索(站内搜索)
互联网的搜索:电商网站,招聘网站,新闻网站,各种app
IT系统的搜索:OA软件,办公自动化软件,会议管理,日程管理,项目管理,员工管理,搜索“张三”,“张三儿”,“张小三”;有个电商网站,卖家,后台管理系统,搜索“牙膏”,订单,“牙膏相关的订单”
搜索,就是在任何场景下,找寻你想要的信息,这个时候,会输入一段你要搜索的关键字,然后就期望找到这个关键字相关的有些信息
如果用数据库做搜索会怎么样
做软件开发的话,或者对IT、计算机有一定的了解的话,都知道,数据都是存储在数据库里面的,比如说电商网站的商品信息,招聘网站的职位信息,新闻网站的新闻信息,等等吧。所以说,很自然的一点,如果说从技术的角度去考虑,如何实现如说,电商网站内部的搜索功能的话,就可以考虑,去使用数据库去进行搜索。
- 比方说,每条记录的指定字段的文本,可能会很长,比如说“商品描述”字段的长度,有长达数千个,甚至数万个字符,这个时候,每次都要对每条记录的所有文本进行扫描,懒判断说,你包不包含我指定的这个关键词(比如说“牙膏”)
 - 还不能将搜索词拆分开来,尽可能去搜索更多的符合你的期望的结果,比如输入“生化机”,就搜索不出来“生化危机”
 
用数据库来实现搜索,是不太靠谱的。通常来说,性能会很差的。
什么是全文检索和Lucene
全文检索:倒排索引
lucene:就是一个jar包,里面包含了封装好的各种建立倒排索引,以及进行搜索的代码,包括各种算法。我们就用java开发的时候,引入lucene jar,然后基于lucene的api进行去进行开发就可以了。用lucene,我们就可以去将已有的数据建立索引,lucene会在本地磁盘上面,给我们组织索引的数据结构。另外的话,我们也可以用lucene提供的一些功能和api来针对磁盘上额
什么是Elasticsearch
Elasticsearch 是一个分布式、RESTful 风格的搜索和数据分析引擎,能够解决不断涌现出的各种用例。 作为 Elastic Stack 的核心,它集中存储您的数据,帮助您发现意料之中以及意料之外的情况。
Elasticsearch的功能、适用场景以及特点
Elasticsearch的功能
- 分布式的搜索引擎和数据分析引擎
搜索:百度,网站的站内搜索,IT系统的检索
数据分析:电商网站,最近7天牙膏这种商品销量排名前10的商家有哪些;新闻网站,最近1个月访问量排名前3的新闻版块是哪些
分布式,搜索,数据分析 - 全文检索,结构化检索,数据分析
全文检索:我想搜索商品名称包含牙膏的商品,select * from products where product_name like "%牙膏%"
结构化检索:我想搜索商品分类为日化用品的商品都有哪些,select * from products where category_id='日化用品'
部分匹配、自动完成、搜索纠错、搜索推荐
数据分析:我们分析每一个商品分类下有多少个商品,select category_id,count(*) from products group by category_id - 对海量数据进行近实时的处理
分布式:ES自动可以将海量数据分散到多台服务器上去存储和检索
海联数据的处理:分布式以后,就可以采用大量的服务器去存储和检索数据,自然而然就可以实现海量数据的处理了
近实时:检索个数据要花费1小时(这就不要近实时,离线批处理,batch-processing);在秒级别对数据进行搜索和分析
跟分布式/海量数据相反的:lucene,单机应用,只能在单台服务器上使用,最多只能处理单台服务器可以处理的数据量 
Elasticsearch的适用场景
- 国外
(1)维基百科,类似百度百科,牙膏,牙膏的维基百科,全文检索,高亮,搜索推荐
(2)The Guardian(国外新闻网站),类似搜狐新闻,用户行为日志(点击,浏览,收藏,评论)+社交网络数据(对某某新闻的相关看法),数据分析,给到每篇新闻文章的作者,让他知道他的文章的公众反馈(好,坏,热门,垃圾,鄙视,崇拜)
(3)Stack Overflow(国外的程序异常讨论论坛),IT问题,程序的报错,提交上去,有人会跟你讨论和回答,全文检索,搜索相关问题和答案,程序报错了,就会将报错信息粘贴到里面去,搜索有没有对应的答案
(4)GitHub(开源代码管理),搜索上千亿行代码
(5)电商网站,检索商品
(6)日志数据分析,logstash采集日志,ES进行复杂的数据分析(ELK技术,elasticsearch+logstash+kibana)
(7)商品价格监控网站,用户设定某商品的价格阈值,当低于该阈值的时候,发送通知消息给用户,比如说订阅牙膏的监控,如果高露洁牙膏的家庭套装低于50块钱,就通知我,我就去买
(8)BI系统,商业智能,Business ntelligence。比如说有个大型商场集团,BI,分析一下某某区域最近3年的用户消费金额的趋势以及用户群体的组成构成,产出相关的数张报表,**区,最近3年,每年消费金额呈现100%的增长,而且用户群体85%是高级白领,开一个新商场。ES执行数据分析和挖掘,Kibana进行数据可视化 - 国内
站内搜索(电商,招聘,门户,等等),IT系统搜索(OA,CRM,ERP,等等),数据分析(ES热门的一个使用场景) 
Elasticsearch的特点
(1)可以作为一个大型分布式集群(数百台服务器)技术,处理PB级数据,服务大公司;也可以运行在单机上,服务小公司
(2)Elasticsearch不是什么新技术,主要是将全文检索、数据分析以及分布式技术,合并在了一起,才形成了独一无二的ES;lucene(全文检索),商用的数据分析软件(也是有的),分布式数据库(mycat)
(3)对用户而言,是开箱即用的,非常简单,作为中小型的应用,直接3分钟部署一下ES,就可以作为生产环境的系统来使用了,数据量不大,操作不是太复杂
(4)数据库的功能面对很多领域是不够用的(事务,还有各种联机事务型的操作);特殊的功能,比如全文检索,同义词处理,相关度排名,复杂数据分析,海量数据的近实时处理;Elasticsearch作为传统数据库的一个补充,提供了数据库所不不能提供的很多功能
lucene和elasticsearch的前世今生
- lucene,最先进、功能最强大的搜索库,直接基于lucene开发,非常复杂,api复杂(实现一些简单的功能,写大量的java代码),需要深入理解原理(各种索引结构)
 - elasticsearch,基于lucene,隐藏复杂性,提供简单易用的restful api接口、java api接口(还有其他语言的api接口)
(1)分布式的文档存储引擎
(2)分布式的搜索引擎和分析引擎
(3)分布式,支持PB级数据 
elasticsearch的核心概念
- Near Realtime(NRT):近实时,两个意思,从写入数据到数据可以被搜索到有一个小延迟(大概1秒);基于es执行搜索和分析可以达到秒级
 - Cluster:集群,包含多个节点,每个节点属于哪个集群是通过一个配置(集群名称,默认是elasticsearch)来决定的,对于中小型应用来说,刚开始一个集群就一个节点很正常
 - Node:节点,集群中的一个节点,节点也有一个名称(默认是随机分配的),节点名称很重要(在执行运维管理操作的时候),默认节点会去加入一个名称为“elasticsearch”的集群,如果直接启动一堆节点,那么它们会自动组成一个elasticsearch集群,当然一个节点也可以组成一个elasticsearch集群
 - Document&field:文档,es中的最小数据单元,一个document可以是一条客户数据,一条商品分类数据,一条订单数据,通常用JSON数据结构表示,每个index下的type中,都可以去存储多个document。一个document里面有多个field,每个field就是一个数据字段。
 - Index:索引,包含一堆有相似结构的文档数据,比如可以有一个客户索引,商品分类索引,订单索引,索引有一个名称。一个index包含很多document,一个index就代表了一类类似的或者相同的document。比如说建立一个product index,商品索引,里面可能就存放了所有的商品数据,所有的商品document。
 - Type:类型,每个索引里都可以有一个或多个type,type是index中的一个逻辑数据分类,一个type下的document,都有相同的field,比如博客系统,有一个索引,可以定义用户数据type,博客数据type,评论数据type。
 - shard:单台机器无法存储大量数据,es可以将一个索引中的数据切分为多个shard,分布在多台服务器上存储。有了shard就可以横向扩展,存储更多数据,让搜索和分析等操作分布到多台服务器上去执行,提升吞吐量和性能。每个shard都是一个lucene index。
 - replica:任何一个服务器随时可能故障或宕机,此时shard可能就会丢失,因此可以为每个shard创建多个replica副本。replica可以在shard故障时提供备用服务,保证数据不丢失,多个replica还可以提升搜索操作的吞吐量和性能。primary shard(建立索引时一次设置,不能修改,默认5个),replica shard(随时修改数量,默认1个),默认每个索引10个shard,5个primary shard,5个replica shard,最小的高可用配置,是2台服务器。
 
在windows上安装和启动Elasticseach
- 安装JDK,至少1.8.0_73以上版本,java -version
 - 下载和解压缩Elasticsearch安装包,目录结构,下载地址:https://www.elastic.co/cn/downloads/elasticsearch,下载版本:5.2.0
 - 启动Elasticsearch:bin\elasticsearch.bat,es本身特点之一就是开箱即用,如果是中小型应用,数据量少,操作不是很复杂,直接启动就可以用了
 - 检查ES是否启动成功:http://localhost:9200/?pretty
// name: node名称
// cluster_name: 集群名称(默认的集群名称就是elasticsearch)
// version.number: 5.2.0,es版本号
{
name: "1LdqLFq",
cluster_name: "elasticsearch",
cluster_uuid: "5pqT0Q_XQky6GKjSiFgilA",
version: {
number: "5.2.0",
build_hash: "24e05b9",
build_date: "2017-01-24T19:52:35.800Z",
build_snapshot: false,
lucene_version: "6.4.0"
},
tagline: "You Know, for Search"
} - 修改集群名称:elasticsearch.yml
 - 下载和解压缩Kibana安装包,使用里面的开发界面,去操作elasticsearch,作为我们学习es知识点的一个主要的界面入口
 - 启动Kibana:bin\kibana.bat。地址:http://localhost:5601
 - 进入Dev Tools界面
 - GET _cluster/health
 
快速入门案例实战之电商网站商品管理:集群健康检查,文档CRUD
document数据格式
应用系统的数据结构都是面向对象的,复杂的
- 对象数据存储到数据库中,只能拆解开来,变为扁平的多张表,每次查询的时候还得还原回对象格式,相当麻烦
 - ES是面向文档的,文档中存储的数据结构,与面向对象的数据结构是一样的,基于这种文档数据结构,es可以提供复杂的索引,全文检索,分析聚合等功能
 - es的document用json数据格式来表达
 
电商网站商品管理案例背景介绍
有一个电商网站,需要为其基于ES构建一个后台系统,提供以下功能:
- 对商品信息进行CRUD(增删改查)操作
 - 执行简单的结构化查询
 - 可以执行简单的全文检索,以及复杂的phrase(短语)检索
 - 对于全文检索的结果,可以进行高亮显示
 - 对数据进行简单的聚合分析
 
简单的集群管理
快速检查集群的健康状况
- es提供了一套api,叫做cat api,可以查看es中各种各样的数据
GET /_cat/health?v
epoch timestamp cluster status node.total node.data shards pri relo init unassign pending_tasks max_task_wait_time active_shards_percent
:: elasticsearch yellow - 50.0%如何快速了解集群的健康状况?green、yellow、red?
green:每个索引的primary shard和replica shard都是active状态的
yellow:每个索引的primary shard都是active状态的,但是部分replica shard不是active状态,处于不可用的状态
red:不是所有索引的primary shard都是active状态的,部分索引有数据丢失了为什么现在会处于一个yellow状态?
我们现在就一个笔记本电脑,就启动了一个es进程,相当于就只有一个node。
现在es中有一个index,就是kibana自己内置建立的index。
由于默认的配置是给每个index分配5个primary shard和5个replica shard,而且primary shard和replica shard不能在同一台机器上(为了容错)。
现在kibana自己建立的index是1个primary shard和1个replica shard。
当前就一个node,所以只有1个primary shard被分配了和启动了,但是一个replica shard没有第二台机器去启动。做一个小实验:此时只要启动第二个es进程,就会在es集群中有2个node,然后那1个replica shard就会自动分配过去,然后cluster status就会变成green状态。
 
快速查看集群中有哪些索引
GET _cat/indices?v
health status index uuid pri rep docs.count docs.deleted store.size pri.store.size
yellow open .kibana xpiNHK4UQb2569AzgiveSw .1kb .1kb
简单的索引操作
- 创建索引
PUT /test_index?pretty
 - 删除索引
DELETE /test_index?pretty
 
商品的CRUD操作
新增商品:新增文档,建立索引
语法:
PUT /index/type/id
{
"json数据"
}
示例:
PUT /ecommerce/product/
{
"name" : "gaolujie yagao",
"desc" : "gaoxiao meibai",
"price" : ,
"producer" : "gaolujie producer",
"tags": [ "meibai", "fangzhu" ]
} {
"_index": "ecommerce",
"_type": "product",
"_id": "",
"_version": ,
"result": "created",
"_shards": {
"total": ,
"successful": ,
"failed":
},
"created": true
} PUT /ecommerce/product/
{
"name" : "jiajieshi yagao",
"desc" : "youxiao fangzhu",
"price" : ,
"producer" : "jiajieshi producer",
"tags": [ "fangzhu" ]
} PUT /ecommerce/product/
{
"name" : "zhonghua yagao",
"desc" : "caoben zhiwu",
"price" : ,
"producer" : "zhonghua producer",
"tags": [ "qingxin" ]
}
es会自动建立index和type,不需要提前创建,而且es默认会对document每个field都建立倒排索引,让其可以被搜索
查询商品:检索文档
语法:
GET /index/type/id
示例:
GET /ecommerce/product/
{
  "_index": "ecommerce",
  "_type": "product",
  "_id": "",
  "_version": ,
  "found": true,
  "_source": {
    "name": "gaolujie yagao",
    "desc": "gaoxiao meibai",
    "price": ,
    "producer": "gaolujie producer",
    "tags": [
      "meibai",
      "fangzhu"
    ]
  }
}
修改商品:替换文档
语法:
PUT /index/type/id
{
"json数据"
}
示例:
PUT /ecommerce/product/
{
"name" : "jiaqiangban gaolujie yagao",
"desc" : "gaoxiao meibai",
"price" : ,
"producer" : "gaolujie producer",
"tags": [ "meibai", "fangzhu" ]
} {
"_index": "ecommerce",
"_type": "product",
"_id": "",
"_version": ,
"result": "updated",
"_shards": {
"total": ,
"successful": ,
"failed":
},
"created": false
}
替换方式有一个不好,即使必须带上所有的field,才能去进行信息的修改(意思是会全部覆盖)
修改商品:更新文档
语法:
POST /index/type/id/_update
{
"json数据"
}
示例:
POST /ecommerce/product//_update
{
"doc": {
"name": "jiaqiangban gaolujie yagao"
}
} {
"_index": "ecommerce",
"_type": "product",
"_id": "",
"_version": ,
"result": "updated",
"_shards": {
"total": ,
"successful": ,
"failed":
}
}
删除商品:删除文档
语法:
DELETE /index/type/id
示例:
DELETE /ecommerce/product/
{
  "found": true,
  "_index": "ecommerce",
  "_type": "product",
  "_id": "",
  "_version": ,
  "result": "deleted",
  "_shards": {
    "total": ,
    "successful": ,
    "failed":
  }
}
快速入门案例实战之电商网站商品管理:多种搜索方式
query string search
搜索全部商品:
GET /ecommerce/product/_search
{
  "took": ,
  "timed_out": false,
  "_shards": {
    "total": ,
    "successful": ,
    "failed":
  },
  "hits": {
    "total": ,
    "max_score": ,
    "hits": [
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": ,
        "_source": {
          "name": "jiajieshi yagao",
          "desc": "youxiao fangzhu",
          "price": ,
          "producer": "jiajieshi producer",
          "tags": [
            "fangzhu"
          ]
        }
      },
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": ,
        "_source": {
          "name": "gaolujie yagao",
          "desc": "gaoxiao meibai",
          "price": ,
          "producer": "gaolujie producer",
          "tags": [
            "meibai",
            "fangzhu"
          ]
        }
      },
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": ,
        "_source": {
          "name": "zhonghua yagao",
          "desc": "caoben zhiwu",
          "price": ,
          "producer": "zhonghua producer",
          "tags": [
            "qingxin"
          ]
        }
      }
    ]
  }
}
took:耗费了几毫秒
timed_out:是否超时,这里是没有
_shards:数据拆成了5个分片,所以对于搜索请求,会打到所有的primary shard(或者是它的某个replica shard也可以)
hits.total:查询结果的数量,3个document
hits.max_score:score的含义,就是document对于一个search的相关度的匹配分数,越相关,就越匹配,分数也高
hits.hits:包含了匹配搜索的document的详细数据
搜索商品名称中包含yagao的商品,而且按照售价降序排序
GET /ecommerce/product/_search?q=name:yagao&sort=price:desc
query string search的由来,因为search参数都是以http请求的query string来附带的
适用于临时的在命令行使用一些工具,比如curl,快速的发出请求,来检索想要的信息;但是如果查询请求很复杂,是很难去构建的
在生产环境中,几乎很少使用query string search
query DSL
DSL:Domain Specified Language,特定领域的语言
优点:更加适合生产环境的使用,可以构建复杂的查询
http request body:请求体,可以用json的格式来构建查询语法,比较方便,可以构建各种复杂的语法,比query string search肯定强大多了
- 查询所有的商品:
GET /ecommerce/product/_search
{
"query": {
"match_all": {}
}
} - 查询名称包含yagao的商品,同时按照价格降序排序
GET /ecommerce/product/_search
{
"query": {
"match": {
"name": "yagao"
}
},
"sort": [
{
"price": {
"order": "desc"
}
}
]
} 分页查询商品,总共3条商品,假设每页就显示1条商品,现在显示第2页,所以就查出来第2个商品
GET /ecommerce/product/_search
{
"query": {
"match_all": {}
},
"from": ,
"size":
}- 指定要查询出来商品的名称和价格就可以
GET /ecommerce/product/_search
{
"query": {
"match_all": {}
},
"_source": ["name","price"]
} 
query filter
搜索商品名称包含yagao,而且售价大于25元的商品
GET /ecommerce/product/_search
{
"query": {
"bool": {
"must": {
"match": {
"name": "yagao"
}
},
"filter": {
"range": {
"price": {
"gt":
}
}
}
}
}
}
full-text search(全文检索)
新增测试数据
PUT /ecommerce/product/
{
"name":"special yagao",
"desc":"special meibai",
"price":,
"producer":"special yagao producer",
"tags":["meibai"]
}
全文模糊检索
GET /ecommerce/product/_search
{
"query" : {
"match" : {
"producer" : "yagao producer"
}
}
}
{
  "took": ,
  "timed_out": false,
  "_shards": {
    "total": ,
    "successful": ,
    "failed":
  },
  "hits": {
    "total": ,
    "max_score": 0.70293105,
    "hits": [
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": 0.70293105,
        "_source": {
          "name": "special yagao",
          "desc": "special meibai",
          "price": ,
          "producer": "special yagao producer",
          "tags": [
            "meibai"
          ]
        }
      },
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": 0.25811607,
        "_source": {
          "name": "gaolujie yagao",
          "desc": "gaoxiao meibai",
          "price": ,
          "producer": "gaolujie producer",
          "tags": [
            "meibai",
            "fangzhu"
          ]
        }
      },
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": 0.25811607,
        "_source": {
          "name": "zhonghua yagao",
          "desc": "caoben zhiwu",
          "price": ,
          "producer": "zhonghua producer",
          "tags": [
            "qingxin"
          ]
        }
      },
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": 0.1805489,
        "_source": {
          "name": "jiajieshi yagao",
          "desc": "youxiao fangzhu",
          "price": ,
          "producer": "jiajieshi producer",
          "tags": [
            "fangzhu"
          ]
        }
      }
    ]
  }
}
phrase search(短语搜索)
跟全文检索相对应,相反,全文检索会将输入的搜索串拆解开来,去倒排索引里面去一一匹配,只要能匹配上任意一个拆解后的单词,就可以作为结果返回
phrase search,要求输入的搜索串,必须在指定的字段文本中,完全包含一模一样的,才可以算匹配,才能作为结果返回
GET /ecommerce/product/_search
{
"query" : {
"match_phrase" : {
"producer" : "yagao producer"
}
}
}
{
  "took": ,
  "timed_out": false,
  "_shards": {
    "total": ,
    "successful": ,
    "failed":
  },
  "hits": {
    "total": ,
    "max_score": 0.70293105,
    "hits": [
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": 0.70293105,
        "_source": {
          "name": "special yagao",
          "desc": "special meibai",
          "price": ,
          "producer": "special yagao producer",
          "tags": [
            "meibai"
          ]
        }
      }
    ]
  }
}
highlight search(高亮搜索结果)
GET /ecommerce/product/_search
{
"query" : {
"match" : {
"producer" : "producer"
}
},
"highlight": {
"fields" : {
"producer" : {}
}
}
}
{
  "took": ,
  "timed_out": false,
  "_shards": {
    "total": ,
    "successful": ,
    "failed":
  },
  "hits": {
    "total": ,
    "max_score": 0.25811607,
    "hits": [
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": 0.25811607,
        "_source": {
          "name": "gaolujie yagao",
          "desc": "gaoxiao meibai",
          "price": ,
          "producer": "gaolujie producer",
          "tags": [
            "meibai",
            "fangzhu"
          ]
        },
        "highlight": {
          "producer": [
            "gaolujie <em>producer</em>"
          ]
        }
      },
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": 0.25811607,
        "_source": {
          "name": "zhonghua yagao",
          "desc": "caoben zhiwu",
          "price": ,
          "producer": "zhonghua producer",
          "tags": [
            "qingxin"
          ]
        },
        "highlight": {
          "producer": [
            "zhonghua <em>producer</em>"
          ]
        }
      },
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": 0.1805489,
        "_source": {
          "name": "jiajieshi yagao",
          "desc": "youxiao fangzhu",
          "price": ,
          "producer": "jiajieshi producer",
          "tags": [
            "fangzhu"
          ]
        },
        "highlight": {
          "producer": [
            "jiajieshi <em>producer</em>"
          ]
        }
      },
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": 0.14638957,
        "_source": {
          "name": "special yagao",
          "desc": "special meibai",
          "price": ,
          "producer": "special yagao producer",
          "tags": [
            "meibai"
          ]
        },
        "highlight": {
          "producer": [
            "special yagao <em>producer</em>"
          ]
        }
      }
    ]
  }
}
快速入门案例实战之电商网站商品管理:嵌套聚合,下钻分析,聚合分析
计算每个tag下的商品数量
//将文本field的fielddata属性设置为true PUT /ecommerce/_mapping/product
{
"properties": {
"tags": {
"type": "text",
"fielddata": true
}
}
} // 聚合计算
GET /ecommerce/product/_search
{
"aggs": {
"group_by_tags": {
"terms": {
"field": "tags"
}
}
}
}
{
  "took": ,
  "timed_out": false,
  "_shards": {
    "total": ,
    "successful": ,
    "failed":
  },
  "hits": {
    "total": ,
    "max_score": ,
    "hits": [
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": ,
        "_source": {
          "name": "jiajieshi yagao",
          "desc": "youxiao fangzhu",
          "price": ,
          "producer": "jiajieshi producer",
          "tags": [
            "fangzhu"
          ]
        }
      },
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": ,
        "_source": {
          "name": "special yagao",
          "desc": "special meibai",
          "price": ,
          "producer": "special yagao producer",
          "tags": [
            "meibai"
          ]
        }
      },
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": ,
        "_source": {
          "name": "gaolujie yagao",
          "desc": "gaoxiao meibai",
          "price": ,
          "producer": "gaolujie producer",
          "tags": [
            "meibai",
            "fangzhu"
          ]
        }
      },
      {
        "_index": "ecommerce",
        "_type": "product",
        "_id": "",
        "_score": ,
        "_source": {
          "name": "zhonghua yagao",
          "desc": "caoben zhiwu",
          "price": ,
          "producer": "zhonghua producer",
          "tags": [
            "qingxin"
          ]
        }
      }
    ]
  },
  "aggregations": {
    "group_by_tags": {
      "doc_count_error_upper_bound": ,
      "sum_other_doc_count": ,
      "buckets": [
        {
          "key": "fangzhu",
          "doc_count":
        },
        {
          "key": "meibai",
          "doc_count":
        },
        {
          "key": "qingxin",
          "doc_count":
        }
      ]
    }
  }
}
不返回hit信息
GET /ecommerce/product/_search
{
"size": ,
"aggs": {
"all_tags": {
"terms": { "field": "tags" }
}
}
}
{
  "took": ,
  "timed_out": false,
  "_shards": {
    "total": ,
    "successful": ,
    "failed":
  },
  "hits": {
    "total": ,
    "max_score": ,
    "hits": []
  },
  "aggregations": {
    "group_by_tags": {
      "doc_count_error_upper_bound": ,
      "sum_other_doc_count": ,
      "buckets": [
        {
          "key": "fangzhu",
          "doc_count":
        },
        {
          "key": "meibai",
          "doc_count":
        },
        {
          "key": "qingxin",
          "doc_count":
        }
      ]
    }
  }
}
对名称中包含yagao的商品,计算每个tag下的商品数量
GET /ecommerce/product/_search
{
"query": {
"match": {
"name": "yagao"
}
},
"size": ,
"aggs": {
"group_by_tags": {
"terms": {
"field": "tags"
}
}
}
}
{
  "took": ,
  "timed_out": false,
  "_shards": {
    "total": ,
    "successful": ,
    "failed":
  },
  "hits": {
    "total": ,
    "max_score": ,
    "hits": []
  },
  "aggregations": {
    "group_by_tags": {
      "doc_count_error_upper_bound": ,
      "sum_other_doc_count": ,
      "buckets": [
        {
          "key": "fangzhu",
          "doc_count":
        },
        {
          "key": "meibai",
          "doc_count":
        },
        {
          "key": "qingxin",
          "doc_count":
        }
      ]
    }
  }
}
先分组,再算每组的平均值,计算每个tag下的商品的平均价格
GET /ecommerce/product/_search
{
"size": ,
"aggs": {
"group_by_tags": {
"terms": {
"field": "tags"
},
"aggs": {
"avg_price": {
"avg": {
"field": "price"
}
}
}
}
}
}
{
  "took": ,
  "timed_out": false,
  "_shards": {
    "total": ,
    "successful": ,
    "failed":
  },
  "hits": {
    "total": ,
    "max_score": ,
    "hits": []
  },
  "aggregations": {
    "group_by_tags": {
      "doc_count_error_upper_bound": ,
      "sum_other_doc_count": ,
      "buckets": [
        {
          "key": "fangzhu",
          "doc_count": ,
          "avg_price": {
            "value": 27.5
          }
        },
        {
          "key": "meibai",
          "doc_count": ,
          "avg_price": {
            "value":
          }
        },
        {
          "key": "qingxin",
          "doc_count": ,
          "avg_price": {
            "value":
          }
        }
      ]
    }
  }
}
计算每个tag下的商品的平均价格,并且按照平均价格降序排序
GET /ecommerce/product/_search
{
"size": ,
"aggs": {
"group_by_tags": {
"terms": {
"field": "tags",
"order": {
"avg_price": "desc"
}
},
"aggs": {
"avg_price": {
"avg": {
"field": "price"
}
}
}
}
}
}
{
  "took": ,
  "timed_out": false,
  "_shards": {
    "total": ,
    "successful": ,
    "failed":
  },
  "hits": {
    "total": ,
    "max_score": ,
    "hits": []
  },
  "aggregations": {
    "group_by_tags": {
      "doc_count_error_upper_bound": ,
      "sum_other_doc_count": ,
      "buckets": [
        {
          "key": "meibai",
          "doc_count": ,
          "avg_price": {
            "value":
          }
        },
        {
          "key": "qingxin",
          "doc_count": ,
          "avg_price": {
            "value":
          }
        },
        {
          "key": "fangzhu",
          "doc_count": ,
          "avg_price": {
            "value": 27.5
          }
        }
      ]
    }
  }
}
按照指定的价格范围区间进行分组,然后在每组内再按照tag进行分组,最后再计算每组的平均价格
GET /ecommerce/product/_search
{
"size": ,
"aggs":{
"group_by_price":{
"range": {
"field": "price",
"ranges": [
{
"from": ,
"to":
},{
"from": ,
"to":
},{
"from": ,
"to":
}
]
},
"aggs": {
"group_by_tags": {
"terms": {
"field": "tags"
},
"aggs": {
"average_price": {
"avg": {
"field": "price"
}
}
}
}
}
}
}
}
{
  "took": ,
  "timed_out": false,
  "_shards": {
    "total": ,
    "successful": ,
    "failed":
  },
  "hits": {
    "total": ,
    "max_score": ,
    "hits": []
  },
  "aggregations": {
    "group_by_price": {
      "buckets": [
        {
          "key": "0.0-20.0",
          "from": ,
          "to": ,
          "doc_count": ,
          "group_by_tags": {
            "doc_count_error_upper_bound": ,
            "sum_other_doc_count": ,
            "buckets": []
          }
        },
        {
          "key": "20.0-40.0",
          "from": ,
          "to": ,
          "doc_count": ,
          "group_by_tags": {
            "doc_count_error_upper_bound": ,
            "sum_other_doc_count": ,
            "buckets": [
              {
                "key": "fangzhu",
                "doc_count": ,
                "average_price": {
                  "value": 27.5
                }
              },
              {
                "key": "meibai",
                "doc_count": ,
                "average_price": {
                  "value":
                }
              }
            ]
          }
        },
        {
          "key": "40.0-50.0",
          "from": ,
          "to": ,
          "doc_count": ,
          "group_by_tags": {
            "doc_count_error_upper_bound": ,
            "sum_other_doc_count": ,
            "buckets": [
              {
                "key": "qingxin",
                "doc_count": ,
                "average_price": {
                  "value":
                }
              }
            ]
          }
        }
      ]
    }
  }
}
Elasticsearch由浅入深(一)的更多相关文章
- Elasticsearch由浅入深(十一)内核原理
		
倒排索引组成结构以及索引不可变原因 对于倒排索引是非常适合用来进行搜索的它的结构:(1)包含这个关键词的document list(2)包含这个关键词的所有document的数量:IDF(invers ...
 - Elasticsearch由浅入深(十一)索引管理
		
索引的基本操作 创建索引 PUT /{index} { "settings": {}, "mappings": { "properties" ...
 - Elasticsearch由浅入深(十)搜索引擎:相关度评分 TF&IDF算法、doc value正排索引、解密query、fetch phrase原理、Bouncing Results问题、基于scoll技术滚动搜索大量数据
		
相关度评分 TF&IDF算法 Elasticsearch的相关度评分(relevance score)算法采用的是term frequency/inverse document frequen ...
 - Elasticsearch由浅入深(九)搜索引擎:query DSL、filter与query、query搜索实战
		
search api的基本语法 语法概要: GET /_search {} GET /index1,index2/type1,type2/_search {} GET /_search { , } h ...
 - Elasticsearch由浅入深(七)搜索引擎:_search含义、_multi-index搜索模式、分页搜索以及深分页性能问题、query string search语法以及_all metadata原理
		
_search含义 _search查询返回结果数据含义分析 GET _search { , "timed_out": false, "_shards": { , ...
 - Elasticsearch由浅入深(六)批量操作:mget批量查询、bulk批量增删改、路由原理、增删改内部原理、document查询内部原理、bulk api的奇特json格式
		
mget批量查询 批量查询的好处就是一条一条的查询,比如说要查询100条数据,那么就要发送100次网络请求,这个开销还是很大的如果进行批量查询的话,查询100条数据,就只要发送1次网络请求,网络请求的 ...
 - Elasticsearch由浅入深(二)ES基础分布式架构、横向扩容、容错机制
		
Elasticsearch的基础分布式架构 Elasticsearch对复杂分布式机制的透明隐藏特性 Elasticsearch是一套分布式系统,分布式是为了应对大数据量. Elasticsearch ...
 - Elasticsearch由浅入深(八)搜索引擎:mapping、精确匹配与全文搜索、分词器、mapping总结
		
下面先简单描述一下mapping是什么? 自动或手动为index中的type建立的一种数据结构和相关配置,简称为mappingdynamic mapping,自动为我们建立index,创建type,以 ...
 - Elasticsearch由浅入深(五)_version乐观锁、external version乐观锁、partial update、groovy脚本实现partial update
		
基于_version进行乐观锁并发控制 先构造一条数据出来 PUT /test_index/test_type/ { "test_field": "test test&q ...
 
随机推荐
- python接口自动化(三十)--html测试报告通过邮件发出去——中(详解)
			
简介 上一篇,我们虽然已经将生成的最新的测试报告发出去了,但是MIMEText 只能发送正文,无法带附件,因此我还需要继续改造我们的代码,实现可以发送带有附件的邮件.发送带附件的需要导入另外一个模块 ...
 - Linux 提升逼格之 命令别名 分享
			
1, 使用场景 Linux下开发 肯定是日常要用命令行的,命令行里包含了众多的命令和工具,例如: git.shell.以及一众系统命令等. 举个例子,码农最常用的 git add ,如果加上别名 可设 ...
 - 作为前端程序员的她凭什么成为Judy团队第一位助教?
			
Judy团队第一位助教-俊英子:正直,阳光,向上,自律,优秀的女孩,当然这些词语还是无法描述出她的优秀 英子,我们第一次的时候,2月25号,下午16:26分,她突然发了一段长的文字我. 她说她一直在读 ...
 - SpringCloud解析之Zuul(二)
			
本文基于Spring Cloud Edgware.SR6,Zuul版本1.3.1,解析Zuul的请求拦截机制,让大家对Zuul的原理有个大概的认识和了解.如有不对的地方,欢迎指正. 在上一期的Spri ...
 - restTemplate重定向问题 &cookie问题
			
最近在做一个转发功能,zuul + ribbon + resttemplate 进行路由.负载.转发的功能 基本准备就绪,在微信自动登陆那遇到了一个坑,ribbon 系统用resttemplate 转 ...
 - 个人永久性免费-Excel催化剂功能第19波-Excel与Sqlserver零门槛交互-查询篇
			
对频繁使用Excel的高级应用的尝试用户来说,绕不过的一个问题Excel的性能问题,对于几万条数据还说得过去,上了10万行的数据量,随便一个函数公式的运算都是一个不小的负荷,有些上进一点的用户会往Ac ...
 - hadoop之安装hadoop
			
官网 http://hadoop.apache.org/ 下载页:https://hadoop.apache.org/releases.html 上传安装包到Linux 解压并进入到目录下 [root ...
 - 2019牛客多校第一场A-Equivalent Prefixes
			
Equivalent Prefixes 传送门 解题思路 先用单调栈求出两个序列中每一个数左边第一个小于自己的数的下标, 存入a[], b[].然后按照1~n的顺序循环,比较 a[i]和b[i]是否相 ...
 - 物联网时代 跟着Thingsboard学IOT架构-CoAP设备协议
			
thingsboard官网: https://thingsboard.io/ thingsboard GitHub: https://github.com/thingsboard/thingsboar ...
 - context创建过程解析(二)之deployWARs
			
HostConfig.deployApps() //在监听到start事件类型,也就是StandardHost调用startInternal protected void deployApps() { ...