现在有一个需求,建立一个知识库,能够对 PDF、doc、excel 类型的资料进行全文搜索。知识库其实是一个信息检索系统(如下图所示),比如搜索引擎,要通过爬虫采集信息、根据规则索引信息、根据用户的查询请求返回信息。
常用的全文搜索引擎有 Elasticsearch 和 Solr 两种,它们都是基于 Apache Lucene 开发而成的。Lucene 则是一个 Java 库,直接使用 Lucene 有一些弊端,比如 Lucene 的使用比较复杂,需要将 Lucene 直接集成到应用程序中等。
Elasticsearch 和 Solr 都是基于 Lucene 开发的,它们隐藏了 Lucene 的复杂性,并具有更优秀的特性。至于选择 Elasticsearch 还是 Solr 可以看这篇文章:全文搜索引擎 ElasticSearch 还是 Solr?。
倒排索引
索引是构成搜索引擎的核心技术之一,信息检索系统使用倒排索引的方式来存储数据。
举例说明什么是倒排索引
索引就像是一本书的目录,目录中包含章节名和页码。通过目录我们可以快速定位到文章内容。倒排索引就像是书后面的术语列表,它会列出一个术语在书中的哪些地方出现过。
再举一个例子,有下面这样一个文档。我们希望输入关键字之后,信息检索系统能够告诉我们哪几个文档包含了输入的关键字。
系统会先将文档进行分词,就像书后面的术语表一样,剔除一些助词,比如:的、得、地,剔除一些没有意义的组合,比如:人工智能这个四个字中,「人工」是一个词,「智能」是一个词,「工智」就不是一个词。这个我们可以通过开源的分词器来完成。
通过分词器,我们可以把文档中的内容划分成一个个词项,并统计词项在文档中出现的频率。比如 Elasticsearch 这个词分别在文档 1、文档 2、文档 3 中出现了 3 次。所以它的词频是 3,倒排记录表为1:1->2:0->3:0
,词频同时也是倒排记录表的长度。
Elasticsearch 中的倒排列表(Posting List)记录了单词对应的文档结合,由倒排索引项(Posting)组成 ,它包括以下 4 项内容:
- 文档 ID
- 词频 TF —— 该单词在文档中出现的次数,用于相关性评分
- 位置(Postion)—— 单位在文档中分词的位置。用于语句搜索(phrase query)
- 偏移(Offset)—— 记录单词的开始结束位置,实现高亮
为什么检索系统要使用倒排索引
倒排索引是存储信息的一种方式,讲到索引我们也很容易想到 MySQL、Oracle 数据库,那么为什么不用关系型数据库来存储文档,并对其进行检索,而用倒排索引呢?原因有以下几点:
- 关系型数据库适合搜索结构化的数据,ES 适合搜索非结构化的数据。结构化的数据比如数据库中的字段,非结构化数据指格式不固定,长度不固定的数据,比如 PDF、word。
- 搜索引擎的数据量大,包含数以亿计的网页,用关系型数据库难以管理这样海量的数据。
- 搜索引擎使用的数据操作更加简单,要求的是响应速度和检索效率。
Elasticsearch 的用途和工作原理
Elasticsearch 是一个分布式的开源搜索和分析引擎,适用于所有类型的数据,包括文本、数字、地理空间、结构化和非结构化数据。Elasticsearch 在 Apache Lucene 的基础上开发而成,由 Elasticsearch N.V.(即现在的 Elastic)于 2010 年首次发布。Elasticsearch 以其简单的 REST 风格 API、分布式特性、速度和可扩展性而闻名,是 Elastic Stack 的核心组件;Elastic Stack 是适用于数据采集、充实、存储、分析和可视化的一组开源工具。人们通常将 Elastic Stack 称为 ELK Stack(代指 Elasticsearch、Logstash 和 Kibana),目前 Elastic Stack 包括一系列丰富的轻量型数据采集代理,这些代理统称为 Beats,可用来向 Elasticsearch 发送数据。
Elasticsearch 在速度和可扩展性方面都表现出色,而且还能够索引多种类型的内容,这意味着其可用于多种用例:应用程序搜索、网站搜索、企业搜索、日志处理和分析、基础设施指标和容器监测、应用程序性能监测、地理空间数据分析和可视化、安全分析、业务分析。
原始数据会从多个来源(包括日志、系统指标和网络应用程序)输入到 Elasticsearch 中。数据采集指在 Elasticsearch 中进行索引之前解析、标准化并充实这些原始数据的过程。这些数据在 Elasticsearch 中索引完成之后,用户便可针对他们的数据运行复杂的查询,并使用聚合来检索自身数据的复杂汇总。在 Kibana 中,用户可以基于自己的数据创建强大的可视化,分享仪表板,并对 Elastic Stack 进行管理。
以上内容摘自官网:什么是 Elasticsearch?
Elasticsearch 各个版本的特性
- 0.4: 2010 年 2 月第一次发布
- 1.0:2014 年 1 月
- 2.0:2015 年 10 月
- 5.0:2016 年 10 月
- 6.0:2017 年 10 月
- 7.0:2019 年 4 月
5.X 新特性:Elasticsearch 的版本从 2.x 直接跳到 5.x 是为了使 ELK 套件的版本统一,从 5.x 之后 ELK 都推荐使用统一的版本。5.x 基于 Lucene 6.x,默认打分机制从 TF-IDF 改为 BM 25。支持 Ingest 节点 / Painless Scripting / Comletion suggested 支持 / 原生 Java REST 客户端。
6.x 新特性基于 Lucene 7.x,支持跨集群复制(CCR) 、索引生命周期管理 、SQL 的支持,全新的基于操作的数据复制框架,可加快恢复数据。
7.x 新特性基于 Lucene 8.0,正式废除单个索引下多 Type 的支持,7.1 开始,Security 功能免费使用。同时提供了 ECK(Elasticsearch Operator on Kubernetes )、New Cluster coordiantion 、Feature-Complete High level REST Client 、Scpipt Score Query 等新特性。
目前(2019年12月1日)最新版本是7.4.2,7.x 做了很大的升级,推荐直接使用 7.x 版本。
ELK Stack
ELK”是三个开源项目的首字母缩写,这三个项目分别是:Elasticsearch、Logstash 和 Kibana。Elasticsearch 是一个搜索和分析引擎。Logstash 是服务器端数据处理管道,能够同时从多个来源采集数据,转换数据,然后将数据发送到诸如 Elasticsearch 等“存储库”中。Kibana 则可以让用户在 Elasticsearch 中使用图形和图表对数据进行可视化。
什么是 ELK Stack?——很简单,指的就是 Elastic Stack。
ELK 使用场景
- 网站搜索 / 垂直搜索 / 代码搜索
- 日志管理与分析 / 安全指标监控 / 应用性能监控 / WEB抓取舆情分
Elasticsearch
Elasticsearch 支持大部系统,具体可以在 Support Matrix 中查看。Elasticsearch 的安装可以查看 Installing Elasticsearch,我用的是当前(2019年12月1日)最新的版本 7.4.2。安装完成之后的目录结构,如下图所示:
启动 Elasticsearch 可以使用 bin/elasticsearch
命令,再通过 http://localhost:9200/
访问,看到下面这样的信息就表示启动成功。
{
"name" : "shuiyujiedeMacBook-Pro.local",
"cluster_name" : "elasticsearch",
"cluster_uuid" : "zBcJ9WboQ9e96xXNMxEHwg",
"version" : {
"number" : "7.4.2",
"build_flavor" : "default",
"build_type" : "tar",
"build_hash" : "2f90bbf7b93631e52bafb59b3b049cb44ec25e96",
"build_date" : "2019-10-28T20:40:44.881551Z",
"build_snapshot" : false,
"lucene_version" : "8.2.0",
"minimum_wire_compatibility_version" : "6.8.0",
"minimum_index_compatibility_version" : "6.0.0-beta1"
},
"tagline" : "You Know, for Search"
}
ELK 都支持插件,使用 bin/elasticsearch-plugin list
查看本机安装了哪些插件,也可以使用 http://localhost:9200/_cat/plugins
来查看插件。安装插件则使用 install 命令,如:bin/elasticsearch-plugin install analysis-icu
。
如果想要启动多个实例,则可以使用如下的方式:
# 启动单节点
bin/elasticsearch -E node.name=node0 -E cluster.name=geektime -E path.data=node0_data
# 多实例
bin/elasticsearch -E node.name=node1 -E cluster.name=geektime -E path.data=node1_data
bin/elasticsearch -E node.name=node2 -E cluster.name=geektime -E path.data=node2_data
bin/elasticsearch -E node.name=node3 -E cluster.name=geektime -E path.data=node3_data
# 删除进程
ps grep | elasticsearch | kill pid
Kibana
Kibana 则可以让用户在 Elasticsearch 中使用图形和图表对数据进行可视化。我们可以在这里下载Kibana。跟随文档提供的 Installation steps 可以启动 Kibana。
Kibana 的使用步骤可以查看这个文档:Set up Kibana。这里提两点,第一点关于插件,ELK 都支持插件对功能进行扩展。可以使用bin/kibana-plugin list
查看插件。更多插件相关内容可以查阅 Know Plugins。
第二点关于汉化,需要在配置文件 kibana.yml
中加入i18n.locale: "zh-CN"
。
Logstash
Logstash 是服务器端数据处理管道,能够同时从多个来源采集数据,转换数据,然后将数据发送到诸如 Elasticsearch 等“存储库”中。
Logstash 的使用也是大同小异,下载 Logstash 的安装包,具体可以查看 Logstash Reference。我们可以下载 MovieLens 这个数据集,接着在 movielens/logstash.conf
文件中配置 csv 文件的地址,通过 Logstash 将数据导入到 Elasticsearch。
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。