前言
突然想写一个关于Elasticsearch
基本使用的文档,因为Elasticsearch
入门的门槛特别低,加上自己很久没有使用了。最近项目接入Elasticsearch
想了想还是写一篇关于基本使用,后面写文章掰开揉碎了分析Elasticsearch
。
本文不会再有表情包出现,是个比较正经的小白入门手册。 大佬就请绕道吧!!!卑微在线祈祷。
看完本篇你对Elasticsearch还是一无所知 哈哈哈哈哈哈哈哈哈
本篇讲的官网文档全都有 唯一的是可以根据代码装个环境自己动手
环境准备
1.首先你要有个docker
docker pull elasticsearch:6.7.2
docker run -d --name elasticsearch -p 9200:9200 -p 9300:9300 -e "discovery.type=single-node" elasticsearch:6.7.2
// 就已经启动成功了 不需要再任何操作
2.其次你 会点php 事实上demo换成任何语言都很简单
3.git clone https://github.com/hongg-coder/es.git
4.用的官方的sdk 对应链接地址packagist 务必提前看下readme
5.debug的数据源大概有1000条 根据下面走 执行脚本自动构建 数据文件在data/user_list.json
数据准备
如果你习惯mysql
可以转变下概念mysql
-> databases
-> talbes
-> rows
-> Colums
elasticsearch
-> Inices
-> Types
-> Documents
-> Fields
来自elasticsearch权威指南说明
demo以简单用户为例子
user_id
用户id 需要范围查询nickname
用户昵称 需要精确查询tag
用户标签 需要多条件查询birthday
用户出生日 需要日期查询mail
用户邮箱 需要精确查询description
用户简介需要分词查询
{
// 用户id
"user_id":1,
// 用户昵称
"nickname":"洪二光",
// 用户标签
"tag":[
"渣男",
"菜鸟"
],
// 出生日期
"birthday":"1994-11-30",
// 邮箱
"mail":"1569498875@qq.com",
// 用户备注
"description":"oh shit"
}
index
定义为user
type
定义为_doc
构建索引
// 按照命令执行 数据自动构建成功
php src/build_index.php
理解两个概念mapping
和analysis
通俗的解释mapping
决定你定义的文档字段类型 analysis
决定对应的文档字段怎么被搜索解析
对应的mapping
{
"user": {
"mappings": {
"_doc": {
"properties": {
"birthday": {
"type": "date",
"format": "yyyy-MM-dd"
},
"description": {
"type": "text",
"analyzer": "standard"
},
"mail": {
"type": "keyword"
},
"nickname": {
"type": "keyword"
},
"tag": {
"type": "keyword"
},
"user_id": {
"type": "integer"
}
}
}
}
}
}
简单理解keyword
和text
keyword
支持
- 精确搜索
- 模糊搜索
- 聚合查询
不支持
- 分词
text
支持
- 精确搜索
- 模糊搜索
- 分词搜索
不支持
- 聚合查询
构建完
curl http://127.0.0.1:9200/user/_doc/_search
// 或者
php src/all_search.php 如果有数据返回说明构建成功
查询篇
查询性能过滤语句 > 查询语句
那么查询语句
常用语全文本搜索(简单理解就是需要用到分词搜索
)
过滤语句
1.精确查询
查询用户id为2的用户
对标mysql
查询select * from user where user_id=2
对应的es语法
GET /user/_doc/_search
{
"query" : {
"term" : { "user_id" : 2 }
}
}
对应的demophp src/search1.php
2.字符串查询
查询邮箱为WcQT9YHGXb@mail.com的用户
对标mysql
查询select * from user where mail='WcQT9YHGXb@mail.com'
GET /user/_doc/_search
{
"query": {
"term": {
"mail": "WcQT9YHGXb@mail.com"
}
}
}
如果查询字符串含有中文 见下方查询语句 1
对应的demophp src/search2.php
3.根据时间查询
查询出生日期 > 1994年11月30日的所有用户
对标mysql
查询select * from user where birthday > '1994-11-30'
GET /user/_doc/_search
{
"query": {
"range": {
"birthday": {
"gt": "1994-11-30"
}
}
}
}
对应的demophp src/search3.php
gt : >
gte : >=
lt : c
lte : <=
4.根据范围查询
查询用户id在1~10的区间内
对标mysql
查询select * from user where user_id in (1,2,3,4,5,6,7,8,9,10)
GET /user/_doc/_search
{
"query": {
"terms": {
"user_id": [
1,
2,
3,
4,
5,
6,
7,
8,
9,
10
]
}
}
}
php src/search4.php
5.单标签查询
查询出标签含有渣男
的所有用户
对标mysql
查询不想对标了! 如果业务涉及标签查询别想用mysql去设计!!
GET /user/_doc/_search
{
"query": {
"term": {
"tag":
"渣男"
}
}
}
php src/search8.php
查询语句
1.精确查询中文字符串 mapping
对应为keyword
查询用户昵称为洪2光
的用户
对标mysql
查询select * from user where realname = '洪2光'
GET /user/_doc/_search
{
"query":{
"match":{
"nickname":"洪2光"
}
}
}
php src/search5.php
2.分词查询字符串 mapping
对应 text
查询用户描述 opportunity R.M. Nixon
相关
对标mysql
查询对标个球球
GET /user/_doc/_search
{
"query":{
"match":{
"description":"opportunity R.M. Nixon"
}
}
}
php src/search6.php
3.精确查询中文字符串 mapping
对应 text
(内心 能不用就别用 如果真有这个场景考虑是不是不要定义为text)
精确查询用户描述为Better an open enemy than a false friend.
对标mysql
查询select * from user where description = 'Be honest rather clever.'
可以试着用上述任何方法去查询 会发现返回没有任何结果。
如果mapping定义text分词还需要同时满足精确搜索 我们需要修改下mapping
"description": {
"type": "text",
"analyzer": "standard",
"fields": {
"keyword": {
"type": "keyword",
"ignore_above": 256
}
}
修改后设置两个field,一个是field倒排索引后的本身,还有一个就是field.keyword(description.keyword),这个字段默认是不分词的,并且最多保留ignore_above
设定长度(字符)
php src/build_index2.php
然后
GET /user/_doc/_search
{
"query": {
"term": {
"description.keyword": "Be honest rather clever."
}
}
}
php src/search7.php
复合查询
1.多标签且查询
查询出标签同时含有渣男
和宅男
的所有用户
GET /user/_doc/_search
{
"query":{
"bool":{
"must":[
{"term":{"tag":"渣男"}},
{"term":{"tag":"宅男"}}
]
}
}
}
php src/search9.php
2.多标签或查询
查询出标签含有渣男
和宅男
其中一个的所有用户
GET /user/_doc/_search
{
"query": {
"terms": {
"tag": [
"渣男",
"宅男"
]
}
}
}
php src/search10.php
3.OR查询
查询邮箱为MGyY5VRs9r@mail.com
或WvJTELTX9d@mail.com
对标mysqlselect * from user where mail ='MGyY5VRs9r@mail.com' or mail = 'WvJTELTX9d@mail.com'
GET /user/_doc/_search
{
"query":{
"bool":{
"should":[
{"term":{"mail":"MGyY5VRs9r@mail.com"}},
{"term":{"mail":"WvJTELTX9d@mail.com"}}
]
}
}
}
php src/search11.php
4.复杂查询1
查询用户id 1到100内 且出生年 大于1994-11-30 且 标签为 渣男的用户
GET /user/_doc/_search
{
"query": {
"bool": {
"must": [
{
"range": {
"birthday": {
"gt": "1994-11-30"
}
}
},
{
"term":{
"tag":"渣男"
}
},
{
"range":{
"user_id":{
"gte":1,
"lte":100
}
}
}
]
}
}
}
php src/search12.php
5.复杂查询2
查询用户id 1到100内 或200到400内 且 标签为 渣男的用户 且 个人简介分词包含 life
、trust
GET /user/_doc/_search
{
"query": {
"bool": {
"should": [
{
"range": {
"user_id": {
"gte": 1,
"lte": 100
}
}
},
{
"range": {
"user_id": {
"gte": 200,
"lte": 400
}
}
}
],
"must": [
{
"term": {
"tag": "渣男"
}
},
{
"match": {
"description": "trust life"
}
}
]
}
}
}
php src/search13.php
就写到这了,关于es不到20%,但是写demo手敲累了(是的,单纯自己累了),剩下自己去摸索吧。
写个最后
先学会用Elasticsearch
再去学原理,下面几篇会把构建索引、解析器包括如何自定义解析器,最后在去学习一些Elasticsearch深层次的东西
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。