ElasticSearch
全文参考 狂神说
视频地址:https://www.bilibiliwww.elastic.co/www.elastic.co/.com/video/BV17a4y1x7zq?from=search&seid=5439246929007048631
前言
Doug Cutting(Hadoop之父),做了一个用于文本搜索的函数库,命名为Lucene(使用java编写),目的是为了给中小型企业增加全文检索功能,且开源。
Lucene 是一套信息检索工具包(jar),包含:索引结构,读写索引的工具,排序,搜索规则。
Nutch是一个建立在Lucene核心之上的网页搜索应用程序,影响力更大。
03年 Google 发布了技术学术论文,介绍了自己的文件系统 GFS(Google File System),是google为了存储海量搜索数据的专用文件系统。
04年,Doug Cutting基于GFS论文,实现了分布式文件存储系统,并且命名为NDFS(Nutch Distributed File System)。
04年,Google再次发布技术学术论文,介绍MapReduce编程模型(用于大规模数据集的并行分析运算)
05年,Doug Cutting基于MapReduce,再Nutch搜索引擎实现该功能。
如此,解决了大数据的两个问题: 存储+计算。
06年,Google再次发布论文,介绍了BigTable,是义中分布式数据存储系统,一种用来处理海量数据的非关系型数据库。
Doug Cutting 在自己的Hadoop系统里 引用了BigTable,并命名为 HBase
而ElasticSearch 就是 Lucene做了 封装和 增强。
一、相关概述
ElasticSearch 简称 ES,是一个开源,高扩展性的分布式全文搜索引擎,它的目的是通过简单的 Restful API 来隐藏 lucene的复杂性。
相关:日志数据分析,logstash采集日志,ES进行复杂的数据分析,ELK技术,elasticSearch+Logstash+kibana
了解ELK
ELK技术,elasticSearch+Logstash+kibana 三大开源框架首字母简称,ES作为底层支持框架,提供搜索能力,logstash是中央数据流引擎,用与从不同目标收集不同格式数据,kibana将数据进行友好展示。
二、与Solr进行比较
-
已有数据(数据量不大)进行搜索时,Solr更快
-
当建立索引时,Solr会产生IO阻塞,Es有明显的优势
-
随着数据量的增加,Solr的效率会越来越低。
-
Solr利用Zookeeper进行分布式管理,而Es自带分布式协调管理功能
-
Solr支持更多格式,Es只支持json
三、ES的安装
jdk1.8、es客户端、kibana工具
相关下载
官网:www.elastic.co/
相关目录
bin 启动目录
config 配置文件
log4j 日志文件
elasticSearch.yml es相关配置
jvm.options jvm配置参数
lib 相关jar包
modules 功能模块
plugins 插件
安装可视化界面 es head
https://github.com/mobz/elasticsearch-head
下载 - 解压 - npm install安装head
- npm run start 启动head
- 配置es 的跨域问题
es 相关配置里输入如下即可:
http.cors.enabled: true
http.cors.allow-origin: "*"
- 启动es 服务
- 通过访问localhost:9100 查看界面
-【初期当作一个数据库来看】后续建立索引(库)、文档(数据)
ES HEAD只作为数据展示(查看索引等),不使用其进行相关查询(不方便 后续使用kibana)
四、Kibana的安装
安装
https://www.elastic.co/cn/downloads/kibana
注意Kibana和Es版本一致。
汉化
修改kibana/config/kibana.yml文件
i18n.locale: "zh-CN"
把cn 换成zh-CN;
x-pack\plugins\translations\translations 目录下 zh-CN.json 文件 配置了汉化设置
启动碰到的问题
## License information could not be obtained from Elasticsearch due to Error: Request Timeout after 30000ms error
启动 kibana.bat 的时候碰到报错的问题
修改了elasticsearch.yml中 增加了 xpack.security.enabled: false
关闭了X-pack 安全空间 启动成功
五、ES核心概念
1、索引
2、mapping (字段类型映射)
3、文档
4、分片(倒排索引)
问题
es是如何存储数据的?数据结构是什么样子?如何实现搜索?
集群,节点,索引,类型,文档,分片,映射都是些什么?
es是面向文档(数据都是json),以下是关系型数据库和es的相关对比
Relational DB | ElasticSearch |
---|---|
数据库(database) | 索引(indies) |
表(table) | 类型(types) [慢慢被弃用 |
行(rows) | 文档(documents) |
列(colunms) | 字段(fields) |
es集群可以包含多个索引,每个索引可以包含多个类型,每个类型下有多个文档,每个文档又包含多个字段
物理设计:
es在后台把每个索引划分成多个分片,每份分下片可以在集群中的不同服务器迁移。
默认的集群名字就是elasticSearch
文档
es面向文档则意味着索引和搜索的最小数据单位是文档,在es中文档有如下几个关键属性:
- 自我包含,一个文档同时包含 key:value
- 可以是具有层次的,参考json
- 灵活的结构 (比如oracle 你要存储数据 需要先定义好列名 才能把数据对应的存放,而es可以忽略或者动态的添加字段)
类型
存疑 前面理解到的类型是表, 但目前看到的类型(映射类型) 却又类似于 数据库相关的字段类型 比如 varchar-text,date 等
答:7.0开始弃用用type, 主要原因是为了增加 ES的检索效率(因为不同type下 名称相同的field在Lucene中的处理方式相同,如此就会出现冲突的情况,导致处理效率下降)
(而这里的类型指代的是mapping映射 也就是 存在索引下的某个字段的类型 如:keyword,date等)
索引
= 数据库
索引是映射类型的容器,且是多个文档的集合,索引存储了映射类型的字段和其他设置,然后存放到各个分片上
节点-分片 如何工作 ()
一个集群至少有一个节点,而一个节点就是一个es进程,节点可以有多个默认索引,如果你创建索引,那么索引将会有五个分片(主分片)构成,每个主分片会有一个副本。
每个节点下会有多个分片, 主副分片不会在同一个节点下,有利于某个节点挂掉之后数据不会丢失。
一个分片是一个lucene索引,一个包含倒排索引的文件目录,倒排索引可以让es不扫描全部文件的情况下就能知道哪些文档包含特定的关键字。
倒排索引 (渣翻译) > 更倾向于翻译为 反向索引
一个未经处理的数据库中,一般是以文档ID作为索引,以文档内容作为记录。
而Inverted index(反向索引) 指的是将单词或记录作为索引,将文档ID作为记录,这样便可以方便地通过单词或记录查找到其所在的文档。
正常情况(正向索引)
找到文档 ,从文档中检索关键字(需要遍历文档)
反向索引:
找到关键字,找到文档编号 得到文档
ES采用lucene倒排索引作为底层,适用于全文搜索
所以一个es的索引由多个lucene索引构成
六、IK分词器
概述
分词:把一段句子或词分成一个个关键字,默认的中文分词是把每个字看成一个词。
如果需要使用中文 建议使用IK分词器 用来满足关键字查询
ik分词器算法
ik_smart 最少切分
ik_max_word 最细颗粒度切分
下载
https://github.com/medcl/elasticsearch-analysis-ik/releases
解压到es的plugins 文件夹下 建立一个新文件夹IK
重启ES kibana
如下:
使用 kibana 测试
ik_max_word
穷尽所有可能分词
ik_smart
最少切分
七、Rest风格相关
method | url | 说明 |
---|---|---|
PUT | 127.0.0.1:9200/索引名/类型名/文档id | 创建文档(指定id) |
POST | 127.0.0.1:9200/索引名/类型名 | 创建文档(随机id) |
POST | 127.0.0.1:9200/索引名/类型名/文档id/_update | 修改文档 |
DELETE | 127.0.0.1:9200/索引名/类型名/文档id | 删除文档 |
GET | 127.0.0.1:9200/索引名/类型名/文档id | 通过id查询文档 |
POST | 127.0.0.1:9200/索引名/类型名/_search | 查询所有文档 |
PUT | 127.0.0.1:9200/索引名/_doc | 根据属性自动分配类型 |
GET | 127.0.0.1:9200/indices?v | 产看所有索引信息 |
相关操作
//添加
PUT /llydemo1/user/3
{
"name":"XX1",
"age":"21",
"desc":"操1作",
"tags":["女","IT"]
}
// 搜索
GET /llydemo1/user/1
// 更新
1.PUT // 弊端: 如果PUT的属性不全,某些属性会被置空
PUT /llydemo1/user/3
{
"name":"lly",
"age":"21",
"desc":"操作",
"tags":["男","IT"]
}
2.POST // 推荐 自由度更高
POST /llydemo1/user/3/_update
{
"doc":{
"name":"修改"
}
}
简单带参数查询
// 简化版
GET llydemo1/user/_search?q=name:修改
GET llydemo1/user/_search //查询头
{ // 查询体
"query":{
// 精确匹配
"match":{
"name":"修改"
}
}
}
"_source" // 控制查询出来的字段 结果过滤
关于分词
trem 直接查询精确的
match 会使用分词器解析
两个类型
text 会被分词器解析 , keyWord 不会被分词器解析
相关整合springboot 依赖
<!-- 自己配置统一的es Version -->
<dependency>
<groupId>org.elasticsearch</groupId>
<artifactId>elasticsearch</artifactId>
<version>${elasticsearch.version}</version>
</dependency>
<dependency>
<groupId>org.elasticsearch.client</groupId>
<artifactId>transport</artifactId>
<version>${elasticsearch.version}</version>
</dependency>
<dependency>
<groupId>org.elasticsearch.client</groupId>
<artifactId>elasticsearch-rest-client</artifactId>
<version>${elasticsearch.version}</version>
</dependency>
<dependency>
<groupId>org.elasticsearch.plugin</groupId>
<artifactId>transport-netty4-client</artifactId>
<version>${elasticsearch.version}</version>
</dependency>