ElasticSearch

1.elasticsearch、Kibana概念,elasticsearch相关术语

1.1 ElasticStack

ElasticSearch:基于json的分布式搜索和分析引擎

搜索、聚合分析、大数据存储

分布式、高性能、高可用、可伸缩、易维护

支持文本搜索、结构化数据、非结构化数据、地址位置搜索等

Logstash:动态数据收集管道,生态丰富。可进行采集、过滤、输出。ElasticSearch是官方首选输出方式,但并非唯一选择

Kibana:数据可视化界面

查询、查看并与存储在ES索引的数据进行交互操作

执行高级的数据分析,并能以图表、表格和地图的形式查看数据

Beats:轻量级的数据采集器

开源、轻量级、即插即用、可扩展

1.2 ElasticSearch

Restful

REST(Representational State Transfer) 表现层状态转化,如果一个架构符合REST原则,则称为RESTFUL架构风格

资源:网络上的一个实体

表现层(Representation):资源呈现出来的形式

状态转化(State Transfer):客户端向操作服务端,使服务端状态发生转化,这种转化是建立在表现层基础上的,故称之为表现层状态转化

REST原则:一个URL表示一个资源,通过HTTP协议中的4个动词GET、POST、PUT、DELETE来对应服务器端的4种操作.GET对应获取资源,POST对应添加或更新资源,PUT对应更新资源,DELETE对应删除资源。

全文检索(Full Text Retrieval)

定义:计算机程序扫描文章中每一个词,给每个词建立一个索引,指明该词在文章出现的次数和位置。当用户查询数据时根据索引查询,类似于字典检索查字。

关键指标:以文本作为检索对象,从文章中找出含有指定词汇的文本。全面、快速和准确是衡量全文检索系统的关键指标。

特点:只处理文本,不处理语义;搜索时英文不区分大小写;结果列表有相关度排序

1.3 ElasticSearch

定义:简称ES,是基于Apache Lucene构建的开源搜索引擎(企业级)。使用java语言编写,提供简单易用的RESTFUL API,使用其开发相关搜索功能,避免了Lucene的复杂性

应用场景

ElasticSearch以轻量级JSON作为数据存储格式,与MongoDB类似,但读写性能优于MongoDB.同时支持地理位置查询,方便地理位置和文本混合查询。以及进行统计、日志类数据存储和分析、可视化方面是引领者。

维基百科、github、stackoverflow、百度、腾讯、新浪、阿里等都使用了ES.

安装

ElasticSearch访问端口是9200

安装之后生产环境 ElasticSearch目录下的data和logs对应数据存放目录和日志存放目录,务必修改

1.3 Kibana

定义:Kibana Navicat是针对Elasticsearch的开源分析及可视化平台。可针对ES索引中的数据查看、查询、交互;也可执行数据分析,并能以图标、表格、地图形式显示数据

端口:默认5601

1.4 ElasticSearch相关术语

接近实时(NRT)(Near Real Time):接近实时搜索,从索引文档到出现结果延迟很低,接近1S内

索引(index):1个索引拥有几分相似特征的文档的集合。由全小写字母组成。可对索引中的文档进行索引、搜索、更新、删除,都需要用到索引名

映射(Mapping):相当于数据库的schema,用于约束字段的数据类型,每种数据类型都有其对应的使用场景。mapping定义了一个文档所包含的所有field信息,每个文档都有映射。但是绝大多数场景中,并不需要手动编写映射,ES实现了动态映射。

ElasticSearch常见数据类型:字符串类型、整数、浮点、逻辑、日期、范围、二进制、数组、对象、嵌套、地理坐标、IP、令牌计数

文档(Document):1个文档是可被索引的最小单元,类似表中的1条记录,采用轻量级的数据交换格式JSON表示

文档类比关系数据库中的1条数据;每个文档都有唯一的ID,类比关系数据库主键ID;json对象由于field构成,field类比关系数据库的column

文档除了基础数据外,还包含元数据(metadata-关于文档的信息),用下划线开头的字段,是官方提供的

_index:文档所属索引名称,即文档存储地方

_type:文档所属类型名字,默认_doc

_id:文档唯一表示。写入时候可以指定此值,不指定,系统会自动生成唯一的UUID值

_score:得分,相关性

_source:文档原始JSON数据

字段(field):相当于数据表的字段,可理解为JSON数据的键,是文档中基本单位,以键值对形式存在

ES和DB关系:

2.ElasticSearch客户端操作索引、映射、文档

通过Kibana的DEV Tools充当Elasticsearch客户端来操作ES

2.1索引基本操作:

创建索引: PUT /索引名

ES中索引状态:red(不可用)、yellow(有风险但可用)、green(健康)

创建索引默认为索引创建1个副本索引和1个分片索引

查询索引: GET /索引名?v

删除索引: DELETE /索引名

删除所有索引:DELETE /* *为通配符,代表所有索引

2.2 映射操作

只有text类型才会进行分词

创建映射:

PUT /索引名

{

"mapping":{

"properties":{

"实际业务字段名":{

"type":"实际业务字段数据类型"

},

"实际业务字段名1":{

"type":"实际业务字段数据类型1"

}

}

}

}

示例:

PUT /products

{

"mapping":{

"properties":{

"title":{

"type":"keyword"

},

"price":{

"type":"double"

}

}

}

}

查询某个索引的映射

语法:GET /索引名/_mapping

示例:GET /products/_mapping

2.3 文档基本操作

添加文档:PUT /索引名/_doc/id

查询文档:GET /索引名/_doc/id

删除文档:DELETE /索引名/_doc/id

更新文档:

第一种方式更新原有数据:

POST /索引名/_update/id

{

"doc":{

"name":"xiaobai"

}

}

第二种方式 添加新的数据:

POST /索引名/_update/id

{

"name":"xiaohong",

"age":11,

"dept":"测试部门",

}

第三种方式 在原基础数据上更新

POST /索引名/_update/id

{

"script":"ctx._source.age+=5"

}

批量操作(非原子操作)

_bulk 批量操作

index 批量添加

delete 批量删除

update 批量更新

批量操作不会因为1个失败而全部失败

3.ElasticSearch高级查询、索引库原理、倒排索引、DSL高级检索

检:根据查询条件查询文档

索:对文档创建索引的过程

3.1 检索方式 _search

ES提供了2种检索方式:通过URL参数进行检索;通过DSL(Domain Specified Language)进行检索。官方推荐使用DSL,因为DSL是基于传递JSON作为请求体格式与ES进行交互,此方式更简洁强大

使用语法

URL查询:GET /索引/类型/_search?参数

示例:

查询某索引下所有数据: GET/索引名/_search?q=*

查询所有并根据age升序:GET /索引名/_search?q=*&sort=age

查询所有并根据age降序:GET /索引名/_search?q=*&sort=age:desc

分页查询(ES默认每页10条):GET /索引名/_search?q=*&sort=age:desc&size=2&from=0

指定显示字段:GET /索引名/_search?q=*&_source=name,age

DSL查询(重点)

基本语法:: GET /索引/类型/_search {}

示例:

查询所有文档:GET /索引名/_search {"query":{"match_all":{}}}

排序(text不支持排序,keyword支持):GET /索引名/_search {"query":{"match_all":{}},"sort":[{"age":{"order":"desc"}},{"address":{"order":"desc"}}]}

DSL高级检索(重点),只列举一部分关键字,其余可至网页中查看

查询所有(match_all-关键字表示返回索引中的全部文档),示例:GET /索引名/_search {"query":{"match_all":{}}}

查询结果中返回指定条数(size),默认返回10条,示例:GET /索引名/_search {"query":{"match_all":{}},"size":1} 表示返回第1条文档

分页查询(from),from关键字指示起始返回位置,和size连用实现分页,示例:GET /索引名/_search {"query":{"match_all":{}},"size":2,from:1}

布尔查询(bool):

must:相当于&&,多个条件必须同时满足

should:相当于||,1个条件满足即可

must_not:相当于!,不能满足任何1个条件

4.ElasticSearch中的分词器,IK分词器介绍

4.1 Analysis和Analyzer

Analysis:文本分析是将全文本转换为一系列单词的过程,也叫分词。Analysis是通过Analyzer来实现的。

分词就是将文档Analyzer分成一个个的Term(关键词查询),每一个Term都指向包含这个Term的文档

Analyzer组成:

StandAnalyzer标准分词器(ES默认分词器),中文进行单字分词,英文根据单词分词

分析器(Analyzer)由三部分构成:character filters(字符过滤器)、tokenizers(分词器)、token filters(Token过滤器)

character filters:文本分词之前,进行预处理。最常见的就是过滤html标签

tokenizers:英文分词根据空格将单词分开,中文分词较为复杂,采用机器学习算法来分词

Token Filters:将切分的单词进行加工。例如大小写转换、去掉停用词、加入同义词等

以上三者顺序:character filters->tokenizers->Token Filters

三者个数:character filters(0个或者多个),tokenizers,Token Filters (0个或者多个)

4.2 内置分词器

StandAnalylzer 默认分词器,英文按照单词切分,并小写处理,中文按照单字分词

Simple Analyzer:按照单词切分(符号被过滤),小写处理

标准分词器测试:POST /索引名 {"analyzer":"standard"}

simple分词器测试:POST /索引名 {"analyzer":"simple"}

4.3 中文分词器(IK分词器):ES中支持多种中文分词器,如smarkCN、IK。首选推荐IK分词器。

安装IK:

IK分词器开源github:https://github.com/medcl/elasticsearch-analysis-ik。注意IK需要和ES版本一致

IK分词器有2种粒度的拆分:

ik_smart:最粗粒度拆分。示例:POST /_analyze {"analyzer":"ik_smart","text":"中华人民共和国"}

ik_max_word:最细粒度拆分。示例:POST /_analyze {"analyzer":"ik_max_word","text":"中华人民共和国"}Client

扩展词、停用词配置

IK支持自定义扩展词典和停用词典

扩展词典:某些词非关键词,但是希望被ES用作检索的关键词,可将这些词加入词典

停用词典:有些词为关键词,但是某些常见不希望这些词被检索到,将这些词放入停用词典

定义扩展字段修改IK分词器目录config文件夹下的IKAnalyzer.cfg.xml文件,通过enrey标签,指定扩展词典和停用词典的文件路径,然后在config目录下创建扩展词典和停用词典的文件(.dic),最后在congig文件夹中创建扩展词典和停用词典对应的文件,在其中添加对应的内容,最后重启ES即可。注意:词典编码必须为UTF-8,否则不生效。

5.过滤查询、聚合查询

5.1 Filter Query 过滤查询

准确说,ES中查询操作分2种,查询和过滤

查询即上述提到的查询,默认会计算每个文档的得分,根据得分排序

过滤只会筛选出符合的文档,并不计算得分,且它可以缓存文档。单从性能考虑,过滤比查询效率更快。

过滤适合大范围筛选数据,查询适合精确匹配数据。一般应用时,先进行过滤,然后使用查询进行精确匹配

过滤语法:GET /索引名/_search {"query":{"filter":{}}}。先执行filter后执行query。ES会缓存经常访问的过滤器,从而加快性能

常见的过滤器模型:

term:过滤某字段关键字为某值的文档

terms:过滤某字段关键字不包含某几个值的文档

ranage:过滤某字段处于某范围的文档

exists:过滤存在指定字段的文档

ids:过滤含有指定字段的索引记录

5.2 聚合查询

简介:Aggregation,是ES除搜索功能外,针对ES数据做统计分析的功能

注意:text类型不支持聚合查询

常见使用:

根据某字段分组:"aggs":{"分组名":{"terms":{"field":"分组的字段"}}}

求最大值:"aggs":{"自定义最大值字段名":{"max":{"field":"取最大值的字段名"}}}

求最小值:"aggs":{"自定义最小值字段名":{"min":{"field":"取最小值的字段名"}}}

求平均值:"aggs":{"自定义平均值字段名":{"avg":{"field":"取平均值的字段名"}}}

求和:"aggs":{"自定义求和字段名":{"sun":{"field":"取和的字段名"}}}

6.spring boot整合RestHighLevelClient(优先)

6.1 RestHighLevelClient介绍

JavaRest有两种模式:

Java Low Level Rest Client:ES官方的低级客户端,通过http与ES集群通信

Java High Level Rest Client: ES官方的高级客户端,基于低级客户端,也是通过http与ES集群通信,提供了更多的接口

注意:Client客户端版本尽量小于等于ES本体的版本,否则出现客户端的使用的API在ES中不支持

优先使用RestHighLevelClient,不建议使用spring-data-elasticsearch。主要原因是灵活性和更新速度,spring将elasticsearch过度封装,开发者很难和DSL查询语句进行关联;其次就是ES更新速度很快,但是spring-data-elasticsearch更新速度比较缓慢。

6.2 引入依赖

引入org.elasticsearch.elasticsearch,org.elasticsearch.client.elasticsearch-rest-client;org.elasticsearch.client.elasticsearch-rest-high-level-client 3个jar包

6.3 ES配置

创建索引

sptingboot项目中application.yml配置文件中配置 elasticsearch的host和port

实体类创建

elasticsearch配置类创建,定义方法,注入RestHighLevelClient

6.4 索引操作

创建索引和映射表结构、获取表结构、删除索引库、判断索引是否存在

6.5 文档操作

增加文档、获取文档、更新文档、删除文档

6.6 Bulk操作

通常从mysql中查询大量数据导入es中

6.7 DSL操作

term(精确查询-和查询字段完全匹配)、terms(精确查询-和terms类似,区别在于terms允许指定多个匹配条件)、全文查询、通配符查询、模糊查询、排序查询、分页查询、

范围查询、bool查询、queryString查询、查询结果过滤、高亮查询、聚合查询(max、min、sum、avg等)、查询集群状态、查询索引信息

7.springboot整合spring-data-elasticsearch

7.1 简介

springdata是用于简化数据库访问、非关系型数据库访问、索引库访问的开源框架。

springdataelasticsearch是基于spring data api简化elasticsearch操作。提供2个对象操作文档,分别是ElasticsearcRepository接口和ElasticsearchRestTemplate,分别提供了对文档的基础操作和复杂操作

优先使用RestHighLevelClient

7.2 引入依赖、yml配置、实体类

引入spring-boot-starter-data-elasticsearch;

application.yml中配置es的URI

定义实体类,使用@Document(indexName="自定义索引名")修饰,指定当前类对应ES中那个索引;使用@Id标记作为id主键的成员变量;使用@Field标记成员变量,标记为文档字段,并映射数据类型

7.3 定义接口继承ElasticSearchRepository接口

使用该接口即可进行简单的CRUD操作;同时也可自定义方法,并且spring data可根据方法名自动实现功能,前提是符合方法定义规定

7.4 使用ElasticSearchRestTemplate进行高级查询

term(精确查询-和查询字段完全匹配)、terms(精确查询-和terms类似,区别在于terms允许指定多个匹配条件)、全文查询、通配符查询、模糊查询、排序查询、分页查询、

范围查询、bool查询、queryString查询、查询结果过滤、高亮查询、聚合查询(max、min、sum、avg等)

8.springboot整合JestClient

8.1 JestClient介绍

非官方提供的ES客户端,此客户端已不再维护,优先使用RestHighLevelClient

8.2 引入依赖

io.searchbox.jest;

8.3 ES配置

application.yml配置es连接属性;

定义JestClientConfig类,注入JsetClient

8.4 JestClient操作ElasticSearch

常用操作和RestHighLevelClient类似

9.ES集群概念、节点故障恢复问题、路由计算、协调节点、倒排索引

9.1 ES集群

由单个或多个ES节点组成,提供负载均衡以及ES搜索吞吐量等功能,避免单节点故障

集群共同持有整个数据,一起提供索引和搜索功能,一个集群有唯一的名字,默认是elasticsearch。节点通过集群名字来加入集群

节点Node:

es实例的java进程,启动时通过-Enode.name指定节点,每个节点都会存储集群的状态信息

集群状态包括:所有节点信息、所有索引及Mapping和Setting,分片路由信息

1个节点是1个集群的一部分,存储的数据参与集群的索引和搜索功能

节点类别:

Data Node:保存分片数据的节点

Coordination Node:协调节点负责接收客户端请求并将请求转发到合适的节点,并负责汇总结果。默认情况下每个节点都有此职责

Hot&Warm Node:不同配置的Data Node组成,主要为了降低成本,Hot节点使用高配置,warm节点使用低配置

分片Shard:ES可将索引划分成多份的能力,每一份即为分片。

创建索引可指定分片数量,每个分片也是功能晚上且独立的"索引",分片可放在集群中任何节点上。

分片针对索引,1个索引的数据由多个分片存储,每个分片又位于不同的节点上。好处在于提高了索引的物理存储,提高了索引的查询速度、吞吐量。

分片允许水平分隔/扩展内容容量;允许在分片上进行分布式/并行操作,进而提高性能/吞吐量

默认情况下,ES中每个索引有1个主分片和1个复制分片。

分片合理配置:分片数和节点数相关,分片数过少影响节点扩容,分片数过多影响查询性能。

副本replicas:

网络/云环境中,某个分片可能中断运行或数据丢失,ES针对此问题,对每个分片提供了1个对应的副本分片,即复制分片,解决数据高可用问题

分配:将分片分配给某节点,是由master节点完成的

9.2 集群健康值检查

健康值状态有以下3种

GREEN:所有主分片和副本分片均为active,集群可正常使用

YELLOW:至少1个副本分片不可用,但是所有主分片都是active,数据仍然可保证数据完整性

RED:至少1个主分片不可用,数据不完整,集群不可用

健康值检查:

GET _cat/health?v

GET _cluster/health

9.3 常用集群部署架构

todo

9.4 单节点集群

集群内只有1个节点,创建索引,包含3个主分片和3个复制分片,位于同一个节点上。主分片都正常,但是副分片都是未启动,因为没有分配任何节点。主分片和副本分片位于同一个节点是没有意义的,因为一旦失去节点,数据也随之丢失。当前集群是yellow状态,可运行,但有丢失数据的风险

9.5 单节点故障转移

集群中只有1个节点运行,会有1个单点故障问题,没有冗余(只有1个节点,副本不会生效)。只需启动第二个节点即可防止数据丢失。如果是在同1台机器上启动多个节点,多个节点只需配置相同的

cluster.name即可加入相同的集群。如果是在不同机器上启动节点,为了保证加入同一集群,需要配置1个可连接到的单播主机列表,防止节点无意中加入集群。

启动第二个节点后,主片和副本会分配在不同的节点上。此时集群状态为:GREEN.

9.6 新增节点到集群

为正在增长的应用程序扩容,当启动第三个节点,集群会为了分散负载而对分片进行重新分配。会实现每个节点上2个分片,每个节点的资源被更少的分片共享,每个分片的性能将会得到提升。

分片是1个功能完整的搜索引擎(底层是Lucene搜索引擎),拥有使用节点上所有资源的能力。上述6个分片最大可扩容到6个节点,每个节点存在1个分片。从而实现每个分片使用每个节点的所有资源

创建索引需要确定主分片的数量,并且永远不可改变此数量,一旦数量变化,那么之前路由的值都会无效,文档再也找不到了

向es中写入文档,是根据公式计算文档应存储至那个分区中,取文档也是根据相同公式,一旦分片数变更,文档自然就找不到。

读操作(搜索数据和返回数据):可同时被主分片和副本分片处理,拥有越多分片数量,吞吐量越高。

因此虽说主分片数量无法修改,但副分片数量可以在集群中动态调整,按需伸缩集群,原来是3个主分片和3个副分片,可将副分片从1变为2,则拥有3个主分片和6个副分片,意味着可将集群中节点

数量扩展为9个,1个节点对应1个分片,相对原来3个节点,集群搜索性能可提升3倍数。

如果节点不变,只是单纯添加副本,性能是不会有变化的,因为每个分片从节点上获取的资源变少,需要提升硬件资源来提高吞吐量。

副本并非越多越好,因为副本越多,数据冗余越多,在大数据的情况下,对存储压力很大。

9.7 集群节点故障

假设集群有3个节点,有1个节点离开集群,那么此时集群还剩2个节点。

如果离开的是主节点,集群为了保证必须有1个主节点运行的原则,所以注解点挂后会立马选举1个新的节点来作为主节点。

如果离开的节点中包含主分片,此时检查集群状态为RED,并非所有主分片都正常工作。但其他节点上存在挂了的主分片的副本的话,新的主节点会将这些分片在其他节点上的副本提升为主分片,此时集群状态是yellow.提升主分片的过程是瞬间的,如果按下开关一般。此时状态非green,是因为一开始设置了每个主分片需要2个副分片,此时每个主分片只有1个副分片,所以集群非green.

但不影响集群运行,如果想恢复为原有状态,原有主节点配置文件中有:discovery.send_hosts["第二个节点的ip加端口","第三个节点的ip加端口"]

9.8 路由计算&分片控制(协调节点)

路由计算

创建的文档如何确定在那个分片中,通过以下公式计算的出

shard = hash(routing)%number_of_primary_shards(主分片数量)

routing是是一个可变值,默认是文档id,也可设置成自定义值。得出结果后,就是文档所处的分片的位置

分片控制(协调节点)

可发送请求到集群中的任一节点,每个节点都有能力处理任意请求(建立在每个节点的分片数据都一样的前提下),每个节点都知道集群中任一文档位置,所以可直接将请求转发到指定的节点上

9.9 数据写流程

新建、索引、删除文档等操作都是写操作,必须在主分片上完成才能复制到相应的副本分片

客户端请求集群任意节点(协调节点)->协调节点将请求转换到指定节点->主分片保存数据------>副本分片保存数据后反馈->主分片反馈->客户端反馈

9.10 数据读流程

接收查询请求->轮询节点,选择节点为协调节点->协调节点计算数据所处分片及全部副本位置->通过轮询策略,将请求转发至其他节点->节点返回查询文档后,返回给客户端

9.11 数据更新流程

客户端接收更新请求->任意节点接收请求(协调节点)->将请求转发至对应的节点->对应节点从主分片中获取数据进而修改数据(如果数据已被另一个进程修改,则此步骤会再次尝试,超过retry_on_conflict次后放弃)->主分片所处节点更新完毕后,新版本文档同步副本分片->副本分片返回成功后,主分片返回成功,协调节点返回客户端成功

9.12 倒排索引

ElasticSearch使用一种倒排索引的数据结构,适用于快速的全文检索

正向索引(foward-index):搜索引擎将文件对应一个文件id,搜索时将id和关键字相对应,形成K-V对,然后对关键字进行统计计数,但是互联网搜索引擎中的文档是天文数字,此结构无法做到实时返回排名结果

倒排索引(inverted-index):为了解决正向索引的问题,搜索引擎会将正向索引重新构建为倒排索引,即将id对应关键字的映射转换为关键字对应文件id的映射,每个关键字都对应一些文件Id,这些文件中都包含这个关键词

倒排索引示例:将2个文档拆分成单独的词,创建1个不包含重复词条的排序列表,包含词汇、及词汇在每个文档中是否存在。

将词条规范为标准模式,可以找到与用户的搜索词不完全一致,但具有足够的相关性。

索引文本和查询字符串必须标准化为相同的格式

相关推荐
java1234_小锋2 小时前
对于GC方面,在使用Elasticsearch时要注意什么?
大数据·elasticsearch·jenkins
Elastic 中国社区官方博客2 小时前
Elasticsearch:Retrievers 介绍
大数据·数据库·人工智能·elasticsearch·搜索引擎·ai·全文检索
xnuscd3 小时前
milvus es
大数据·elasticsearch·milvus
傻啦嘿哟16 小时前
Flask项目中PostgreSQL与Elasticsearch的批量更新
elasticsearch·postgresql·flask
java1234_小锋19 小时前
Elasticsearch在部署时,对Linux的设置有哪些优化方法?
大数据·elasticsearch·搜索引擎
疯狂吧小飞牛19 小时前
elasticsearch单节点模式部署
运维·elasticsearch
白衣神棍1 天前
ES更新问题 Failed to close the XContentBuilder异常
java·elasticsearch
Java 第一深情1 天前
Linux上安装单机版Kibana6.8.1
elasticsearch·kibana
LeonNo111 天前
ElasticSearch学习了解笔记
笔记·学习·elasticsearch
iPrologue1 天前
自己记录docker和ES集群
elasticsearch·docker·容器