Elasticsearch介绍

Elasticsearch介绍

一、认识Elasticsearch

Elasticsearch 是一个分布式、可扩展、实时的搜索与数据分析引擎,它能从项目一开始就赋予开发者的数据以搜索、分析和探索的能力,这是通常没有预料到的。它存在还因为原始数据如果只是躺在磁盘里面根本就毫无用处

Elasticsearch 不仅仅只是全文搜索,还可以用于结构化搜索、数据分析、复杂的人类语言处理、地理位置和对象间关联关系等, Elasticsearch 是一个实时的分布式搜索分析引擎,它能让你以前所未有的速度和规模,去探索你的数据,它被用作全文检索、结构化搜索、分析以及这三个功能的组合:

Elasticsearch 是一个开源的搜索引擎,建立在一个全文搜索引擎库 Apache Lucene基础之上,Lucene 可以说是当下最先进、高性能、全功能的搜索引擎库—无论是开源还是私有

但是 Lucene 仅仅只是一个库。为了充分发挥其功能,你需要使用 Java 并将 Lucene 直接集成到应用程序中。 更糟糕的是,您可能需要获得信息检索学位才能了解其工作原理,Lucene 非常 复杂

Elasticsearch 也是使用 Java 编写的,它的内部使用 Lucene 做索引与搜索,但是它的目的是使全文检索变得简单, 通过隐藏 Lucene 的复杂性,取而代之的提供一套简单一致的 RESTful API

然而,Elasticsearch 不仅仅是 Lucene,并且也不仅仅只是一个全文搜索引擎, 它可以被下面这样准确的形容:

一个分布式的实时文档存储,每个字段 可以被索引与搜索

一个分布式实时分析搜索引擎

能胜任上百个服务节点的扩展,并支持 PB 级别的结构化或者非结构化数据

Elasticsearch 将所有的功能打包成一个单独的服务,这样你可以通过程序与它提供的简单的 RESTful API 进行通信, 可以使用自己喜欢的编程语言充当 Web 客户端,甚至可以使用命令行(去充当这个客户端)

二、Elasticsecrch安装使用

  • 安装
  • 需要一台虚拟机 contos7 虚拟机(建议8G内存),尝试4G内存
1、使用管理员root登录centos,10.10.12.93,要求至少4G内存,下载安装包
 
wget https://artifacts.elastic.co/downloads/elasticsearch/elasticsearch-6.3.1.tar.gz
 

 
 2、创建一个用户esuser

 adduser esuser

 

 3、上传elasticsearch-6.3.1.tar.gz到/home/esuser下

 
 
 4、解压
 cd /home/esuser/
 tar -zxvf elasticsearch-6.3.1.tar.gz

 
 
 5、创建用户,创建目录,修改目录所属用户
 cd /home/esuser/
 mkdir -p esdata/data
 mkdir -p esdata/log
 chown -R esuser elasticsearch-6.3.1 
 chown -R esuser esdata

 
 
 6、修改es的配置文件,可以使用提供好的elasticsearch.yml覆盖即可
 cp /home/esuser/elasticsearch-6.3.1/config/elasticsearch.yml /home/esuser/elasticsearch-6.3.1/config/elasticsearch.yml.bak
 vi /home/esuser/elasticsearch-6.3.1/config/elasticsearch.yml

 
 
(1)配置服务名称:将17行的注释去掉 
 cluster.name: my-application
 
(2)配置服务名称:将23行的注释去掉
 node.name: node-1
 
(3)配置es数据的存放路径:将33行的注释去掉,修改33行
 path.data: /home/esuser/esdata/data
 
(4)配置es日志的存放路径:将37行的注释去掉,修改37行
 path.logs: /home/esuser/esdata/log
 
(5)配置内存锁:将43行的注释去掉
 bootstrap.memory_lock: true
 
(6)配置服务的ip和端口:将55行的注释去掉,修改55行
 network.host: 0.0.0.0
 
(7)配置服务的端口:将59行的注释去掉
 http.port: 9200
 
(8)配置节点:将68行的注释去掉
 discovery.zen.ping.unicast.hosts: ["host1", "host2"]
 
(9)配置节点:将80行的注释去掉,修改80行
 gateway.recover_after_nodes: 1
 
(10)配置节点:将88行的注释去掉
 action.destructive_requires_name: true

 7、配置系统参数
 
 (1)vi /etc/security/limits.conf
 在最后添加如下4行内容:
 esuser hard nofile 65536
 esuser soft nofile 65536
 esuser soft memlock unlimited
 esuser hard memlock unlimited
 
 (2)vi /etc/sysctl.conf
在最后添加如下1行内容:
 vm.max_map_count = 262144
 
(3)执行命令
 sysctl -p
 
(4)执行命令
 visudo
 
在101行添加1行内容:
 esuser  ALL=(ALL)       ALL
 
 (5)vi /etc/security/limits.d/90-nproc.conf
 添加2行内容:
 soft nofile 204800
 hard nofile 204800
 
 (6)vi /etc/security/limits.d/def.conf
 添加2行内容:
 soft nofile 204800
 hard nofile 204800
 
8、启动,不能使用root用户启动
 (1)安装java环境
 
 yum install java -y
 su esuser
 cd /home/esuser/elasticsearch-6.3.1/bin
 ./elasticsearch
 
9、关闭防火墙
 systemctl stop firewalld
 
 10、访问
 http://10.10.12.93:9200/

三、Postman使用

Postman是一款功能强大的网页调试与发送网页HTTP请求的Chrome插件

在开发或者调试网络程序或者是网页B/S模式的程序的时候是需要一些方法来跟踪网页请求的,用户可

以使用一些网络的监视工具比如著名的Firebug等网页调试工具,而Postman不仅可以调试简单的

CSS、HTML、脚本等简单的网页基本信息,它还可以发送几乎所有类型的HTTP请求!而我们需要的功

能就是Postman的请求接口功能,在没有学习Python API的前提下,我们使用Postman来进行操作

下载地址 https://www.postman.com/downloads/

四、Python操作ES

  • 创建ES模型
put
10.10.12.93:9200/mycar/
{
    "mappings": {
        "car": {
            "properties": {
                "name": {
                    "type": "keyword"
                },
                "buydate": {
                    "type": "date",
					"format":"yyyy-MM-dd"
                },
                "nowprice": {
                    "type": "float"
                },
                "oldprice": {
                    "type": "float"
                },
                "km": {
                    "type": "float"
                },
                "city": {
                    "type": "text"
                },
                "year": {
                    "type": "integer"
                },
                "day": {
                    "type": "integer"
                }
            }
        }
    }
}

  • Python操作ES

  • 安装模块elasticsearch

    pip install elasticsearch

    (1)插入数据

from elasticsearch import Elasticsearch
import random

ls1 = ["红旗", "哈弗", "吉利", "奔驰", "宝马", "奥迪", "丰田", "本田", "大众", "福特", "吉普"]
ls2 = ["A", "B", "C", "D", "E", "F", "S"]
ls3 = ['广州市', '深圳市', '珠海市', '汕头市', '佛山市', '韶关市', '湛江市', '肇庆市', '江门市', '茂名市', '惠州市', '梅州市', '汕尾市', '河源市', '阳江市',
       '清远市', '东莞市', '中山市', '潮州市', '揭阳市', '云浮市', '增城市', '从化市', '南雄市', '乐昌市', '英德市', '连州市', '台山市', '开平市', '鹤山市',
       '恩平市', '廉江市', '雷州市', '吴川市', '高州市', '化州市', '信宜市', '高要市', '四会市', '兴宁市', '陆丰市', '阳春市', '普宁市', '罗定市']
es = Elasticsearch("10.10.12.87", port=9200)

for i in range(100):
    data = {
        "name": random.choice(ls1) + random.choice(ls2) + str(random.randint(100, 1000)),
        "nowprice": random.randint(10, 100),
        "oldprice": random.randint(10, 100) + random.randint(1, 5),
        "km": random.randint(0, 30),
        "city": random.choice(ls3),
        "buydate": "{}-{}-{}".format(random.randint(2000, 2020), random.randint(1, 12), random.randint(1, 28)),
        "year": 1,
        "day": 30
    }
    ret = es.index(index="mycar", body=data, doc_type="car")
    print(ret)

es.close()

五、ES基本使用

es和数据库mysq进行类比学习

mysql database table column row
es index type field document

传统的数据库只能存储基本数据类型(字符串,数字,日期)

对于复杂的关系模型需要使用一对一,一对多,多对多完成

但是es没有主外键,可以直接保存复杂的数据,通过键值对

1、索引

创建索引,使用put请求

在es中,创建索引同时会创建类型,并且在es6版本认为一个索引中只有一个类型,es7准备删除类型,现在我们es6,类型只需要一个起一个无关逻辑的名字

创建索引和类型,需要在路由上描述索引,然后搭建请求的数据结构

属性 说明
car 索引,名称必须小写
mappings 映射,是创建的开始
suibian 类型名称,随便定义
properties 属性
name 字段名称
type 字段类型的键
text 文本类型

Es常用的字段类型

类型 描述
string 字符串类型
long 64位存储,数字类型
integer 32位存储,数字类型
short 16位存储,数字类型
byte 8位存储,数字类型
double 64位双精度存储,数字类型
float 32位双精度存储,数字类型
data 日期类型,必须指定格式
Boolean 布尔类型
Binary 二进制类型
Array 数组类型
Object 单个json(字典)对象
nested 嵌套的json对象
text 文本类型,用于全文本字段,文本不会被Analyzer分词默认不支持聚合和排序,需要将fielddata设置为true
Keyword 用于ID,枚举及不需要分词的文本适用于Filter精确匹配,Sorting和Aggregations
  • 创建索引
{
    "mappings":{     # 固定的
        "suibain":{     # 类型名,随便写
            "properties":{   # 固定的,字段和类型
                "name":{    # 字段的名字
                    "type":"keyword"  # 字段的类型keyword是字符串类型,不支持分词
                },   
                "description":{
                    "type":"text"   # text时候字符串类型,默认支持分词
                }
            }
        }
    }
}
  • 查询所有索引

路由:http://10.10.12.87:9200/_cat/indices/

yellow 代表当前索引当中索引的状态,绿色代表健康,黄色代表有警告,红色代表有错误

open 代表索引开启 close

car 索引名

  • 查询单个索引

路由:http://10.10.12.87:9200/索引的名字

  • 新增索引数据

路由:http://10.10.12.87:9200/索引的名字/索引的类型/

  • 查询索引数据

路由:http://10.10.12.87:9200/car/_search/

  • 精确查询term
get
10.10.12.87:9200/mycar/_search
{
    "query":{
        "term":{
            "name":"吉利A406"
        }
    }
}

# 多条件精确查询 terms
{
    "query":{
        "terms":{
            "name":["吉利A406","奔驰E316"]
        }
    }
}
  • 查询所有match_all
get
10.10.12.87:9200/mycar/_search
{
    "query":{
        "match_all":{
            
        }
    }
}
  • 查询-分页from size

from 起始位置

size 分页显示的个数

从0开始,查询10个

get
10.10.12.87:9200/mycar/_search
{
    "query": {
        "match_all": {}
    },
    "from": 0,
    "size": 2
}

分页,每页显示20(page_size)条,查询的第page_now页

page_now page_age=20
1 from 0,size 20
2 from 20,size 20
n form (n-1)*20,size 20
  • 查询-排序sort
  • 默认是正序
{
    "query": {
        "match_all": {}
    },
    "sort":"buydate"
}
{
    "query": {
        "match_all": {}
    },
    "sort":{
        "buydate":{
            "order":"desc"
        }
    }
}
  • 查询-模糊查询match

​ match会被分词,而keyword不会被分词,match的需要跟keyword的完全匹配可以

​ match分词,text也分词,只要match的分词结果和text的分词结果有相同的就匹配

分词:因为英文单词是靠空格分开,分词只需要按照空格分开即可,但是中文中间默认没有空格,怎么进行分词呢?

python有jieba分词java有ik分词,这里选择这个ik,注意必须与es版本保持一致

将ik的分词包上传es的plugins中,然后重启es服务

修改es模型(删除,新建),将name设置为text,支持存储分词(将内容分词之后存储,而不是存储原始内容)

get
10.10.12.87:9200/mycar/_search
{
    "query": {
        "match": {
            "name":"宝马"
        }
    }
}
  • 逻辑查询 bool

    must:文档必须匹配must所包括的查询条件,相当于and

    should:文档应该匹配should所包括的查询条件其 中的一个或多个,相当于or

    must_not:文档不能匹配must_not所包括的该查询条件,相当于not

get
10.10.12.87:9200/mycar/_search
# must查询
{
    "query":{
        "bool":{
            "must":[
                {
                    "term":{
                        "km":20
                    }
                },
                {
                    "term":{
                        "year":1
                    }
                }
            ]
        }
    }
}
# should查询
{
    "query":{
        "bool":{
            "should":[
                {
                    "term":{
                        "km":20
                    }
                },
                {
                    "term":{
                        "year":1
                    }
                }
            ]
        }
    }
}

# must_not查询
{
    "query":{
        "bool":{
            "must_not":[
                {
                    "term":{
                        "km":20
                    }
                },
                {
                    "term":{
                        "year":10
                    }
                }
            ]
        }
    }
}
  • 查询-范围查询range
符号 含义
lt 小于
gt 大于
lte 小等于
gte 大等于
{
    "query": {
        "range":{
            "oldprice":{
                "lt":100,
                "gt":10
            }
        }
    }
}
  • 分词与不分词

    1、keyword不分词 text分词

    2、match会分词 term不会分词

    https://www.cnblogs.com/chenmz1995/p/10199147.html

    https://github.com/medcl/elasticsearch-analysis-ik/releases

    https://github.com/medcl/elasticsearch-analysis-ik/releases/download/v6.3.1/elasticsearch-analysis-ik-6.3.1.zip

    ik分词器有两种分词模式:ik_max_word和ik_smart模式

    1、ik_max_word

    会将文本做最细粒度的拆分,比如会将“中华人民共和国人民大会堂”拆分为“中华人民共和国、中华人民、中华、 华人、人民共和国、人民、共和国、大会堂、大会、会堂等词语

    2、ik_smart

    会做最粗粒度的拆分,比如会将“中华人民共和国人民大会堂”拆分为中华人民共和国、人民大会堂。 测试两种分词模式:

  • 测试分词

    get
    10.10.12.87:9200/_analyze
    {
        "text": "中华人民共和国人民大会堂"
    }
    {
        "text": "中华人民共和国人民大会堂",
        "analyzer":"ik_max_word"
    }
    
    
    # 字符串包括text和keyword两种类型: text默认支持分词,keyword不支持分词
    # (1)analyzer 通过analyzer属性指定分词器
    
    "name": { 
    	"type": "text", 
    	"analyzer":"ik_max_word" 
    }
    # 指定name的字段类型为text,使用ik分词器的ik_max_word分词模式
    
    # (2)上边指定了analyzer是指在索引和搜索都使用ik_max_word,如果单独想定义搜索时使用的分词器则可以通过 search_analyzer属性
    
    "name": { 
        "type": "text", 
        "analyzer":"ik_max_word", 
        "search_analyzer":"ik_smart" 
    }
    
    # 对于ik分词器建议是索引时使用ik_max_word将搜索内容进行细粒度分词,搜索时使用ik_smart提高搜索精确性
    
    # (3)index 通过index属性指定是否索引, 默认为index=true,即要进行索引,只有进行索引才可以从索引库搜索到
    "name": { 
        "type": "text", 
        "index":false 
    }
    

你可能感兴趣的:(Tornado)