ElasticSearch是一个基于Lucene的搜索服务器。它提供了一个分布式的全文搜索引擎,其对外服务是基于RESTful web接口发布的。Elasticsearch是用Java开发的应用,并做为Apache许可条款下的开放源码发布,是当前流行的企业级搜索引擎。设计用于云计算中,可以达到近实时搜索,稳定,可靠,快速,安装使用方便。java
cluster集群。ElasticSearch集群由一或多个节点组成,其中有一个主节点,这个主节点是能够经过选举产生的,主从节点是对于集群内部来讲的。ElasticSearch的一个概念就是去中心化,字面上理解就是无中心节点,这是对于集群外部来讲的,由于从外部看ElasticSearch集群,在逻辑上是个总体,你与集群中的任何一个节点通讯和与整个ElasticSearch集群通讯是等价的。也就是说,主节点的存在不会产生单点安全隐患、并发访问瓶颈等问题。node
primary shard:表明索引的主分片,ElasticSearch能够把一个完整的索引分红多个primary shard,这样的好处是能够把一个大的索引拆分红多个分片,分布存储在不一样的ElasticSearch节点上,从而造成分布式存储,并为搜索访问提供分布式服务,提升并发处理能力。primary shard的数量只能在索引建立时指定,而且索引建立后不能再更改primary shard数量(从新分片须要从新定义分片规则)。es5.x以后默认为5,es7.x默认为1。程序员
replica shard:表明索引主分片的副本,ElasticSearch能够设置多个replica shard。replica shard的做用:一是提升系统的容错性,当某个节点某个primary shard损坏或丢失时能够从副本中恢复。二是提升ElasticSearch的查询效率,ElasticSearch会自动对搜索请求进行负载均衡,将并发的搜索请求发送给合适的节点,加强并发处理能力。可取值为0~n,默认为1。web
索引。至关于关系型数据库中的表。其中存储若干类似结构的Document数据。如:客户索引,订单索引,商品索引等。ElasticSearch中的索引不像数据库表格同样有强制的数据结构约束,在理论上,能够存储任意结构的数据。但了为更好的为业务提供搜索数据支撑,仍是要设计合适的索引体系来存储不一样的数据。数据库
类型。每一个索引中都必须有惟一的一个Type,Type是Index中的一个逻辑分类。ElasticSearch中的数据Document是存储在索引下的Type中的。json
注意:ElasticSearch5.x及更低版本中,一个Index中能够有多个Type。ElasticSearch6.x版本以后,type概念被弱化,一个index中只能有惟一的一个type。且在7.x版本以后,删除type定义。api
文档。ElasticSearch中的最小数据单元。一个Document就是一条数据,通常使用JSON数据结构表示。每一个Index下的Type中均可以存储多个Document。一个Document中可定义多个field,field就是数据字段。如:学生数据({"name":"张三", "age":20, "gender":"男"})。数组
对数据进行分析,抽取出数据中的词条,以词条做为key,对应数据的存储位置做为value,实现索引的存储。这种索引称为倒排索引。倒排索引是Document写入ElasticSearch时分析维护的。安全
3,比数据库作搜索的优点服务器
GET _cat/health?v
其中status的状态分为三种:green、yellow和red
#查看健康状态 GET _cat/health?v #查看节点信息 GET _cat/nodes?v #查看索引信息 GET _cat/indices?v #查看分片信息 GET _cat/shards?v
#建立my_index索引(settings能够省略),建立后shards分片数不能修改,只能修改shards副本数 PUT my_index { "settings": { "number_of_shards": 5, "number_of_replicas": 1 } }
在ElasticSearch中,默认的建立索引的时候,会分配5个primary shard,并为每一个primary shard分配一个replica shard(在ES7版本后,默认建立1个primary shard)。在ElasticSearch中,默认的限制是:若是磁盘空间不足15%的时候,不分配replica shard。若是磁盘空间不足5%的时候,再也不分配任何的primary shard。ElasticSearch中对shard的分布是有要求的。ElasticSearch尽量保证primary shard平均分布在多个节点上。Replica shard会保证不和他备份的那个primary shard分配在同一个节点上。
#修改索引 PUT my_index/_settings { "number_of_replicas": 2 }
注意:索引一旦建立,primary shard数量不可变化,能够改变replica shard数量。
DELETE my_index
GET _cat/indices?v
在索引中增长文档。在index中增长document。
ElasticSearch有自动识别机制。若是增长的document对应的index不存在,自动建立index;若是index存在,type不存在,则自动建立type。若是index和type都存在,则使用现有的index和type。
PUT 索引名/类型名/惟一ID{字段名:字段值}
#若是当前id已经存在,那么就是修改,若是不存在就是新增
PUT my_index/_doc/1 { "name":"test_doc_01", "remark":"first test elastic search", "order_no":1 }
若是当前索引中的document的id已经存在,那么就是修改,若是不存在就是新增。可是若是此时id已经存在,想要强制新增会报错,强制新增的语法为:
PUT 索引名/类型名/惟一ID/_create{字段名:字段值} 或者是 PUT 索引名/类型名/惟一ID?op_type=create{字段名:字段值}
此操做为ElasticSearch自动生成id的新增Document方式。此语法格式和PUT请求的数据新增,只有惟一的区别,就是能够自动生成主键id,其余的和PUT请求新增数据彻底一致。
POST 索引名/类型名[/惟一ID]{字段名:字段值}
#此时,若是新增时惟一id(2)不存在就是新增,若是惟一id(2)存在就是修改。这个与PUT相同
#能够直接变为没有id,会随机生成一个GUID做为id
POST my_index/_doc { "name":"test_doc_02", "remark":"second test elastic search", "order_no":2 }
GET 索引名/类型名/惟一ID
GET my_index/_doc/1
批量查询能够提升查询效率。推荐使用(相对于单数据查询来讲)。
#语法 GET 索引名/类型名/_mget { "docs" : [ { "_id" : "惟一ID值" }, { "_id" : "惟一ID值" } ] }
PUT|POST 索引名/类型名/惟一ID{字段名:字段值}
本操做至关于覆盖操做。全量替换的过程当中,ElasticSearch不会真的修改Document中的数据,而是标记ElasticSearch中原有的Document为deleted状态,再建立一个新的Document来存储数据,当ElasticSearch中的数据量过大时,ElasticSearch后台回收deleted状态的Document。
PUT my_index/_doc/1 { "name":"test_doc_01111", "remark":"first 111", "order_no":1111 }
POST 索引名/类型名/惟一ID/_update{doc:{字段名:字段值}}
只更新某Document中的部分字段。这种更新方式也是标记原有数据为deleted状态,建立一个新的Document数据,将新的字段和未更新的原有字段组成这个新的Document,并建立。对比全量替换而言,只是操做上的方便,在底层执行上几乎没有区别。
POST my_index/_doc/1/_update { "doc":{ "name":" test_doc_01_for_update" } }
DELETE 索引名/类型名/惟一ID
ElasticSearch中执行删除操做时,ElasticSearch先标记Document为deleted状态,而不是直接物理删除。当ElasticSearch存储空间不足或工做空闲时,才会执行物理删除操做。标记为deleted状态的数据不会被查询搜索到。
DELETE my_index/_doc/2
定义:
POST _bulk { "action_type" : { "metadata_name" : "metadata_value" } } { document datas | action datas } action_type: create: 强制建立,至关于PUT 索引名/类型名/惟一ID/_create index : 普通的PUT操做,至关于建立Document或全量替换 update: 更新操做(partial update),至关于 POST 索引名/类型名/惟一ID/_update delete: 删除操做
案例:
#若是index和type为同一个能够提出来,此时建立ID为111,覆盖ID为1,修改ID为2,删除ID为3 POST my_index/_doc/_bulk {"create":{"_id":111}} {"name":"zs","age":15} {"index":{"_id":1}} {"name":"first","sort":1} {"update":{"_id":2}} {"doc":{"sort":2}} {"delete":{"_id":3}}
注意:bulk语法中要求一个完整的json串不能有换行。不一样的json串必须使用换行分隔。多个操做中,若是有错误状况,不会影响到其余的操做,只会在批量操做返回结果中标记失败。bulk语法批量操做时,bulk request会一次性加载到内存中,若是请求数据量太大,性能反而降低(内存压力太高),须要反复尝试一个最佳的bulk request size。通常从1000~5000条数据开始尝试,逐渐增长。若是查看bulk request size的话,通常是5~15MB之间为好。
bulk语法要求json格式是为了对内存的方便管理,和尽量下降内存的压力。若是json格式没有特殊的限制,ElasticSearch在解释bulk请求时,须要对任意格式的json进行解释处理,须要对bulk请求数据作json对象会json array对象的转化,那么内存的占用量至少翻倍,当请求量过大的时候,对内存的压力会直线上升,且须要jvm gc进程对垃圾数据作频繁回收,影响ElasticSearch效率。
生成环境中,bulk api经常使用。都是使用java代码实现循环操做。通常一次bulk请求,执行一种操做。如:批量新增10000条数据等。
Mapping在ElasticSearch中是很是重要的一个概念。决定了一个index中的field使用什么数据格式存储,使用什么分词器解析,是否有子字段等。
在上述的自动mapping字段类型分配的时候,只有text类型的字段须要分词器。默认分词器是standard分词器。
GET 索引名/_mapping
{ "my_index": { # 索引名 "mappings": { # 映射列表 "my_type": { # 类型名 "properties": { # 字段列表 "age": { # 字段名 "type": "long" # 字段类型 }, "gender": { #字段名 "type": "text", #字段类型 "fields": { # 子字段列表 "keyword": { # 子字段名 "type": "keyword", # 子字段类型,keyword不进行分词处理的文本类型。gender.keyword能够进行排序 "ignore_above": 256 # 子字段存储数据长度 } } } } } } } }
能够经过命令,在建立index和type的时候来定制mapping映射,也就是指定字段的类型和字段数据使用的分词器。
手工定制mapping时,只能新增mapping设置,不能对已有的mapping进行修改。
如:有索引a,其中有类型b,增长字段f1的mapping定义。后续能够增长字段f2的mapping定义,可是不能修改f1字段的mapping定义。
PUT 索引名称 { "mappings":{ "类型名称":{ "properties":{ "字段名":{ "type":类型, ["analyer":字段的分词器,] ["fields":{ "子字段名称":{ "type":类型, "ignore_above":长度限制 } }] } } } } }
例如:
PUT test_index { "settings": { "number_of_shards": 2, "number_of_replicas": 1 }, "mappings": { "test_type":{ "properties": { "author_id" : { "type": "byte", "index": false }, "title" : { "type": "text", "analyzer": "ik_max_word", "fields": { "keyword" : { "type": "keyword", "ignore_above": 256 } } }, "content" : { "type": "text", "analyzer": "ik_max_word" }, "post_date" : { "type": "date" } } } } } "index" - 是否能够做为搜索索引。可选值:true | false "analyzer" - 指定分词器。 "type" - 指定字段类型
PUT 索引名/_mapping/类型名 { "properties":{ "新字段名":{ "type":类型, "analyer":字段的分词器, "fields":{ "子字段名":{ "type":类型, "ignore_above":长度 } } } }
例如:
PUT /test_index/_mapping/test_type { "properties" : { "new_field" : { "type" : "text" , "analyzer" : "standard" } } }
GET 索引名称/_analyze { "field":"索引中的text类型的字段名", "text":"要分词处理的文本数据" }
例如:
#测试content字段的分词效果
GET test_index/_analyze { "field": "content", "text": "我是一个程序员" }