本文根据ElasticSearch官方文档整理所得,简单介绍ElasticSearch的概念以及一些简单的检索方法数据库
首先下载ElasticSearch和Kibana到本地,注意这两个东西的版本号要一致,而后启动Kibana,打开http://localhost:5601/app/kibana便可进入GUI的管理界面,进入Dev Tools便可操做ES。json
先看ES中,索引的两个概念:app
存储数据到 Elasticsearch 的行为叫作 索引(动词) ,但在索引一个文档以前,须要肯定将文档存储在哪里。负载均衡
一个 Elasticsearch 集群能够包含多个索引 (名词),相应的每一个索引能够包含多个类型。这些不一样的类型存储着多个文档* 每一个文档又有多个属性 。分布式
能够看到上述语句不是很通顺,主要是因为这里的索引有两个意思:spa
例子:rest
PUT /megacorp/employee/1
{
"first_name" : "John",
"last_name" : "Smith",
"age" : 25,
"about" : "I love to go rock climbing",
"interests": [ "sports", "music" ]
}
复制代码
路径/megacorp/employee/1
包含了三部分的信息:megacorp就是索引名称(像数据库),employee(像一张表),1(特定employee,就像标识每一行的主键)。接下来的JSON就是储存的内容了。code
检索文档就像HTTP请求同样,执行一个GET请求便可取回JSON文档:排序
GET /megacorp/employee/1
索引
相似的GET还能够改成HEAD、DELETE等。
搜索全部雇员:
GET /megacorp/employee/_search
查询JSON中的任意指定字段:
GET /megacorp/employee/_search?q=last_name:Smith
使用查询表达式搜索,它支持构建更加复杂和健壮的查询,使用请求体。:
GET /megacorp/employee/_search
{
"query" : {
"match" : {
"last_name" : "Smith"
}
}
}
复制代码
GET /megacorp/employee/_search
{
"query" : {
"bool": {
"must": {
"match" : {
"last_name" : "smith"
}
},
"filter": {
"range" : {
"age" : { "gt" : 30 }
}
}
}
}
}
复制代码
全文搜索能够完成传统关系型数据库很难作到的事情,如搜索全部喜欢攀岩的雇员:
GET /megacorp/employee/_search
{
"query" : {
"match" : {
"about" : "rock climbing"
}
}
}
复制代码
这彷佛与以前没什么不一样啊?可是请看返回结果:
"hits": [
{
"_index": "megacorp",
"_type": "employee",
"_id": "1",
"_score": 0.53484553,
"_source": {
"first_name": "John",
"last_name": "Smith",
"age": 25,
"about": "I love to go rock climbing",
"interests": [
"sports",
"music"
]
}
},
{
"_index": "megacorp",
"_type": "employee",
"_id": "2",
"_score": 0.26742277,
"_source": {
"first_name": "Jane",
"last_name": "Smith",
"age": 32,
"about": "I like to collect rock albums",
"interests": [
"music"
]
}
}
]
复制代码
Elasticsearch 默认按照相关性得分排序,即每一个文档跟查询的匹配程度。第一个最高得分的结果很明显:John Smith 的 about
属性清楚地写着 “rock climbing” 。可是Jane也返回了,可是因为他的关键字里并无彻底匹配,因此他的相关性没有John的高,排在后面。而传统的关系型数据库则是要么匹配要么彻底不匹配。
那若是我想像关系型数据库同样只匹配彻底符合的怎么办呢?就是用短语匹配的查询:match_phrase
GET /megacorp/employee/_search
{
"query" : {
"match_phrase" : {
"about" : "rock climbing"
}
}
}
复制代码
则只会返回彻底匹配的John的文档。
在使用聚合agg以前须要先对查询的字段加上fileddata=true,由于文档中写道
Fielddata can consume a lot of heap space, especially when loading high cardinality
text
fields.
fileddata会消耗大量的堆空间,因此默认是关闭的,在这里要手动打开。
PUT megacorp/_mapping/employee/
{
"properties": {
"interests": {
"type": "text",
"fielddata": true
}
}
}
复制代码
有点像Group By:如找出Employee中最受欢迎的兴趣爱好:
GET /megacorp/employee/_search
{
"aggs": {
"all_interests": {
"terms": { "field": "interests" }
}
}
},
复制代码
在输出中能够看到,每一个interest按照人数排序:
{
...
"hits": { ... },
"aggregations": {
"all_interests": {
"buckets": [
{
"key": "music",
"doc_count": 2
},
{
"key": "forestry",
"doc_count": 1
},
{
"key": "sports",
"doc_count": 1
}
]
}
}
}
复制代码
这个aggs字段还能够做为query字段的子查询。如:
GET /megacorp/employee/_search
{
"query": {
"match": {
"last_name": "smith"
}
},
"aggs": {
"all_interests": {
"terms": {
"field": "interests"
}
}
}
}
复制代码
还支持分级汇总,如查询每一个兴趣的员工平均年龄:
GET /megacorp/employee/_search
{
"aggs" : {
"all_interests" : {
"terms" : { "field" : "interests" },
"aggs" : {
"avg_age" : {
"avg" : { "field" : "age" }
}
}
}
}
}
复制代码
Elasticsearch 尽量地屏蔽了分布式系统的复杂性。这里列举了一些在后台自动执行的操做: