es 常用操作

一:索引相关

1,创建索引 
(1) PUT /majian_index/
{
    "settings":{
        "index":{
            "number_of_shards":3,
            "number_of_replicas":0
            }

    }
}

(2)创建索引的同时手动创建mapping(一般添加数据的时候,mapping可以自动创建,_routing 表示自定义路由,默认是以id为路由,只有在特殊用法的情况下才需要自定义路由,如果不指定路由自定,默认查所有分片,然后聚合返回结果)

 PUT /majian_index/

{
    "settings":{
        "index":{
            "number_of_shards":3,
            "number_of_replicas":0
            }

    },
    "mappings":{
        "user3":{

            "_routing":{

              "required":true

            },
            "properties":{
                "name":{"type":"text"},
                "age":{"type":"long"},
                "date":{"type":"date","index":false}
            }
        }
    }
}

(3)也可以直接用 PUT majian_index2 (添加索引,用默认配置,注意put要大写)

2:查看索引 

    (1),查看集群健康:GET /_cat/health?v

    (2),查看所有索引:GET /_cat/indices?v
    (3),查看某个索引信息:GET /majian_index/_settings/  
    (4),查看所有索引信息 GET /_all/_settings
(7)GET /majian_index1/user/_mapping 来查看mapping
(6)GET /majian_index/_settings?flat_settings=true (flat_settings=true 参数通过对象.属性的方式返回设置信息)

    (5)查看集群状态 GET /_cluster/state(后面可以加上filter_path参数来指定返回哪些字段)
(5)查看集群状态 GET /_cluster/settings

   

3: 删除索引:
DELETE majian_index

二:文档相关curd

1:插入

(1),PUT /majian_index/user1/1  (user1 表示索引下的类型,这个类型是我们自定义的,1 表示id,用put 方法必须指定id
(put是更新,如果没有的话就插入))
{
  "name":"zhangsan",
  "age":30
}

(2)可以通过op_type参数来指定,强制创建索引(如果索引已经存在的话会返回失败)第二种是通过 (PUT majian_index/user/1/_create)

PUT majian_index/user/1?op_type=create
{
"user" : "kimchy",
"post_date" : "2009-11-15T14:12:12",
"message" : "trying out Elasticsearch"
}
(2),POST /majian_index/user1/ (如果不指定id 的话,id就由es 生成,那么就要用post方法)
{
  "name":"zhangsan",
  "age":30
}

2:删除某个文档

(1),DELETE /majian_index/user1/1 (删除id=1 的)
(2) DELETE /afs_service1/user1/1?wait_for_active_shards=3&timeout=5s (wait_for_active_shards通过这个参数可以控制有几个节点可用时再操作)
(3) POST /afs_service1/user1/_delete_by_query (删除符合查询条件的)
{
"query":{
"match":{
"content":"zhaoliu"
}
}
}
也可以用 POST /afs_service1/user1/_delete_by_query?q=content:liqi (这种方式)
(_delete_by_query 在开始文档删除时,先获取一个快照,再删除,如果这两步之间文档的版本发生变化时,删除会失败,会发生版本冲突
将会发生多次搜索,然后删除,如果有的成功了,有的失败了,失败的会返回)

(4)POST /afs_service1/user1/_delete_by_query (删除所有文档)
{
"query": {
"match_all": {}
}
}

(5) POST /majian_index1/user1/_delete_by_query?routing=wangwu (如果删除的时候指定了路由,只会删除指定路由上的数据,即使查询的是所有)
{
"query":{
"match_all":{}
}
}

(6)POST twitter/_delete_by_query?scroll_size=5000 (默认使用的scroll_size为1000,一次删1000条?)
{
"query": {
"term": {
"user": "kimchy"
}
}
}
(7) _delete_by_query 还支持这些参数(refresh, wait_for_completion, wait_for_active_shards, timeout, and scroll)

(8) POST twitter/_delete_by_query?conflicts=proceed (conflicts=proceed 在出现错误是,继续执行后面的,而不是终止)
{
"query": {
"match_all": {}
}
}


3:修改记录

(1),put是更新,如果没有的话就插入(这个是覆盖的方式,就是必须要加上所有的字段,如果只要更新某一个字段,就要用post 方法如下:)
(2),跟新某个字段,如下把id=1 的年龄改为100  :  (有就修改,没有就新增)
POST /majian_index/user1/1/_update
    {
        "doc":{
            "age":100
        }    
    }
    
(3) POST /afs_service1/user1/1/_update (如果名字本来就是zhangsan的话,这个操作想当与没做任何修改,es不会去执行,
返回结果中有noop表示空操作,版本号也不会更新,如果想更新版本号的话就加上 "detect_noop": false)
{
"doc":{
"name":"zhangsan"
},
"detect_noop": false
}

(4),POST /afs_service1/user1/_update_by_query?conflicts=proceed (这一种,只有查询,没有更新体的,只会更新版本号)
{
"query":{
"term":{
"name":"zhangsan"
}
}

}

(5) POST /afs_service1/user1/1/_update (脚本更新文档,lang表示用何种脚本,painless表示es内置脚本,还有pyton,js等)
{
"script":{
"source":"ctx._source.age=ctx._source.age+params.aaa",
"lang":"painless",
"params":{
"aaa":11
}
}
}

(6)更新数组
先插入带数组的数据
PUT /afs_service1/user1/6
{
"name":"zhangliu",
"age":60,
"content":"zhangliu love apple",
"likes":["apple","banana"]
}

更新(添加一条)

POST /afs_service1/user1/6/_update
{
"script": {
"source":"ctx._source.likes.add('graps')",
"lang": "painless"
}
}
或者使用参数的方式
POST /afs_service1/user1/6/_update
{
"script": {
"source":"ctx._source.likes.add(params.aaa)",
"lang": "painless",
"params":{
"aaa":"orange"
}
}
}

(7)删除 (注意remove 参数只能是 索引号,如果只包含脚本的话,script后面就没有花括号,要包含lang,params等就要包含花括号)
POST /afs_service1/user1/6/_update
{
"script": {
"source":"if(ctx._source.likes.contains(params.aaa)){ctx._source.likes.remove(ctx._source.likes.indexOf(params.aaa))}",
"lang": "painless",
"params":{
"aaa":"orange"
}
}
}

除了 _source 通过ctx可以访问的还有 index, _type, _id, _version, _routing and _now

(8) 可以对指定文档添加一个字段
POST afs_service1/user1/1/_update
{
"script" : "ctx._source.name = 'zhangsan'"
}

也可对指定文档删除一个字段
POST /afs_service1/user1/1/_update
{
"script":"ctx._source.remove('name')"
}

(8) 还可以删除(op=delete,下面就是如果id为1 的记录中 name=zhangsan,那么删除这条记录,如果不符合条件的话,就只会增加版本号)

POST afs_service1/user1/1/_update
{
"script":"if(ctx._source.name=='zhangsan'){ctx.op='delete'}"
}

(9) 如果这个id的文档不存在的话,就会插入 upsert 中的内容
POST afs_service1/user1/7/_update
{
"script":"ctx._source.name='lisi'",
"upsert":{
"name":"zhangsan7",
"age":70,
"content":"zhangqi love grape"
}
}

(10)如果 想 id为8 的文档 不存在的话,就插入 script中的内容,而不是插入 upsert中的内容的话,就设置 "scripted_upsert": true,
POST /afs_service1/user1/8/_update
{
"scripted_upsert": true,
"script": {
"source":"ctx._source.likes=params.likes",
"params": {
"likes":["apple","grape"],
"content":"zhangsan8 like apple"
}
},
"upsert": {}
}

(11) 通过将 doc_as_upsert":true 设置为true 可以在文档不存在时可以插入doc中的内容(正常情况下id为9 的不存在的话,去更新会报错)
POST afs_service1/user1/9/_update
{
"doc":{
"name":"zhang9"
},
"doc_as_upsert":true

}

2,_update_by_query(批量更新,更新时获取的索引的快照,这意味着 获取索引快照后,更新前,数据可能改变,这是更新将终止
后面的所有元素都做为失败元素返回(在failures字段中返回),如果想,冲突时继续执行后面的记录 可以 加上参数 conflicts=proceed)

(1),名字为张三的都改为李四(这个更新即使 query中的name就是李四 也会更新(版本号)不会有noop空操作,这个和 _update 不一样 _update不会更新版本号,会返回noop空操作)
如果不想更新版本号可以在 script后加上ctx.op='noop'表示允许空操作,如果想删除 query查询的文档可以 在scirpt 中设置 ctx.op='delete'
可以在url后加上routing字段路由到指定的分片上,默认情况下滚动查询批次为1000 可以使用scroll_size=100 来指定一次查多少(也就是更新多少)
还可以 使用 pipeline 来指定管道(?待办,还有 throttling 代办,requests_per_second 代办) _update_by_query 还支持这些参数( pretty, refresh, wait_for_completion, wait_for_active_shards, timeout and scroll)
(scroll表示搜索的存活时间默认5分钟 scroll=10m 10分钟)

POST /majian_index1/_update_by_query
{
"script": {
"source": "ctx._source.name='lisi';ctx.op='noop'",
"lang": "painless"
},
"query": {
"term": {
"name": "zhangsan"
}
}
}

4:查看

(1),GET /majian_index/user1/1 (查看指定索引下,指定类型,指定id=1的记录)

(2),GET /majian_index/user1/1?_source=name,age (就是mysql 的 select name,age where id=1)    


    
六,重新索引
1,reindex重新索引指的是把数据从一个索引复制到另一个索引,不负责创建目的索引(需要自己创建 maapping,sharding 等)
下面是把majian_index1 重新索引到majian_index2(majian_index2要事先建好)
POST _reindex
{
"source": {
"index": "majian_index1"
},
"dest": {
"index": "majian_index2"
}
}   

2,一般把索引复制到一个新的索引时,不太可能会发生版本冲突,但想忽略版本冲突,强制复制到新的索引上可以设置 version_type字段
为 internal 如果设置为 external 将会替换(目标索引的版本号比源索引的小时,会覆盖)

POST _reindex
{
"source": {
"index": "majian_index1"
},
"dest": {
"index": "majian_index2",
"version_type": "internal"
}
}

POST _reindex
{
"source": {
"index": "majian_index1"
},
"dest": {
"index": "majian_index2",
"version_type": "external"
}
}

七:批量获取 

下面这四个方法只对 id的能这样写?,id 换成其他字段就不行了
1,(指定索引,类型,id)
GET /_mget/
{
    "docs":[
    {
        "_index":"majian_index1",
        "_type":"user1",
        "_id":1
    },
    {
        "_index":"majian_index2",
        "_type":"user2",
        "_id":1
    }
        
    ]
}

2,也可以指定获取的列(select name,, 获取多个列的话就是 "_source":["name","age"])

GET /_mget/
{
    "docs":[
    {
        "_index":"majian_index1",
        "_type":"user1",
        "_id":1,
        "_source":"name"
    },
    {
        "_index":"majian_index2",
        "_type":"user2",
        "_id":1,
        "_source":"name"
    }
        
    ]
}

3,获取同索引同类型下的不同文档(上面是获取不同索引,不同类型下的文档,6.x以后同一个索引下只有一个type)

GET /majian_index/user1/_mget
{
    "docs":[
    {
        "_id":1
        "_source":"name"
    },
    {
        "_id":1
        "_source":"name"
    }
        
    ]
}

4,也可以进一步简化(注意和上面的对比,少了docs, 并且id 是ids 而不是_id)

GET /majian_index1/user1/_mget
{
        "ids":[1,2]
}

5,bulk 批量操作(能批量添加,修改,删除,而上面的mget只能批量查询)

模式:
{action:{metadata}}
{requestBody}

其中
action表示行为有(create,index,update,delete, create和index表示创建文档,create是文档不存在时,创建,
如果文档存在时,create就会报错,index,是没有就创建,有就替换)

metadata 表示具体数据,也就是我们要添加的,修改的,删除的跟新的文档数据,有 index,type,id
requestBody 表示请求体,(注意删除是没有请求体的)

(1)批量添加
POST /majian_index1/user1/_bulk

{"index":{"_id":3}}
{"name":"wangwu","age":30}

{"index":{"_id":4}}
{"name":"zhaoliu","age":40}

注意,这里面的请求体里面没有包含索引,和类型信息,就表示使用url中的,如果包含的话,就是新建索引
如下新建了,majian_index2 索引,类型user2
POST /majian_index1/user1/_bulk
{"index":{"_index":"majian_index2","_type":"user2","_id":1}}
{"name":"zhangsan","age":20}

(2)删除  
POST /majian_index1/user1/_bulk
{delete:{"_index":"majian_index1","_type":"user1","_id":1}}

(3)修改
POST /majian_index1/user1/_bulk
{"update":{"_index":"majian_index1","type":"user1","_id":1}}
{"doc":{"age":100}}

总结: bulk 一次能处理多大的数据量取决于硬件,因为bulk 是把要处理的数据放入内存中的,一般建议1000-5000
5-15M 最大不能超过100M,可以在es的配置文件中配置


九,es 版本控制

(1)内部版本控制:es内部的版本控制是通过乐观锁来控制的(必须版本号相等才行,和mysql一样)_version 比如下面修改版本号为3 的记录

PUT /majian_index1/user1/1?version=3
{
    "name":"zhangsan",
    "age":30
}
(2)外部版本控制:比如当有这样一种需求,mysql版本号用时间戳来表示,但是我们想把mysql的数据,导入到es中,
这个时候我们可以用外部版本号(就是把es中的版本号替换成我们url中提供的版本号),只有外部版本号大于es中的
版本号才能成功比如下面,假如es中内部的版本号为1,我们提供的版本号为 20181222 那么会把es中的版本号
1,替换成 20181222  注意后面的参数version_type=external 表示外部版本号

PUT /majian_index1/user1/1?version=20181222&version_type=external
{
    "name":"zhangsan",
    "age":30
}


九:mapping

(1)当我们创建文档的时候,比如 PUT /majian_index1/user1/1 的时候,es 不仅为我们创建了索引index,和类型type
还为我们自动创建了mapping 可以通过下面的语法查询mapping

GET /majian_index1/user/_mapping 来查看mapping

(2)手动创建mapping:如果自动创建mapping可以满足要求的话,就不必手动创建mapping
 如果要手动创建mapping的话,可以按下面语法创建(注意下面的"index":false 是mapping的一个属性表示不索引,es
 默认情况下会为每一个字段都创建 索引,有些没必要创建索引的,就不用创建索引)

{
    "settings":{
        "index":{
            "number_of_shards":3,
            "number_of_replicas":0
            }

    },
    "mappings":{
        "user3":{
            "properties":{
                "name":{"type":"text"},
                "age":{"type":"long"},
                "date":{"type":"date","index":false}
            }
        }
    }
}
 


 基本查询###################################### 
 
 
 
 
 
 十 es的基本查询(query查询)


 query_string(查询)
1, GET /majian_index/user/_search?q=name:zhangsan&sort=name:desc
 2,分页查询  : GET/majian/_index/user/_search?from=0&size=2  (从0开始查2个)

3,可以通过filter_path 指定返回哪些字段 GET/majian/_index/user/_search?filter_path=took,hits.hits

只能到_source一级,不能再往下了(注意和_source的区别)


//1,term 查询(查询条件只能是一个字段)
 (1)GET /majian_index/user/_serach
{
    "query":{
        "term":{"name":"zhangsan"}
    }


//2,terms 查询查询张三或李四(查询条件只能有一个字段)
(2)GET /majian_index/user/_serach
{
    "query":{
        "terms":{"name":["zhangsan","lisi"]}
    }


//2,from表示从哪个文档开始,size表示查几个,就是mysql中的分页
(3)GET /majian_index/user/_serach
{    "from":0,
    "size":10,
    "query":{
        "terms":{"name":["zhangsan","lisi"]}
    }

//2,如果想获取版本号 加上 version:true 就行
(4)GET /majian_index/user/_serach
{    "from":0,
    "size":10,
    "version":true,
    "query":{
        "terms":{"name":["zhangsan","lisi"]}
    }


//3,match 查询(查询条件也只能是一个字段,和term 查询的区别是 match可以进行分词)
//zhangsan lisi 会进行分词成zhangsan, lisi,(注意和term 查询的区别,term 查询的时候,查询条件不会分词,比如有条记录 是 zhangsan and lisi, term查询条件为zhangsan,那么也会把这条记录查询出来,),而match 会对查询条件进行分词)
(3)GET /majian_index/user/_serach
{    
    "query":{
        "match":{"name":"zhangsan lisi"}
    }

}
//查询年龄为30 的
(2)GET /majian_index/user/_serach
{    
    "query":{
        "match":{"age":"30"}
    }

}

//查询 所有
(3)GET /majian_index/user/_serach
{    
    "query":{
        "match_all":{}
    }

}

//4,查询 多个字段(查询name 或 age 的值为 zhangsan 的)
(1)GET /majian_index/user/_serach
{    
    "query":{
        "multi_match":{
        "query":"zhangsan",
        "fields":["name","age"]
        }
    }

}

//4,短语查询,也就是 mysql 中的 like %value% 比如下面 就是查%zhangsan,lisi% (相当于不分词了)
(2)GET /majian_index/user/_serach
{    
    "query":{
        "match_phase":{
        "name":"zhangsan,lisi"
        }
    }

}


//指定返回字段 通过_source  也就是mysql 中的 select 列
(6)GET /majian_index/user/_serach
{    "_source":["name","age"]
    "query":{
        "name":"zhangsan"
    }

}


//通过includs ecludes 来指定包含哪些字段,排除哪些字段
(7)GET /majian_index/user/_serach
{    
    "query":{
        "match_all":{}
    }
    "_source":{
    
    "includes":["name","age"],
    "ecludes":["score","grade"]
    
    }

}

//通过includs ecludes 来指定包含哪些字段,排除哪些字段(可以使用通配符)
(7)GET /majian_index/user/_serach
{    
    "query":{
        "match_all":{}
    }
    "_source":{
    
    "includes":"nam*",
    "ecludes":["score","grade*"]
    
    }

}

4,排序:

//根据年龄升序
1,GET /majian_index/user/_search
{
    "query":{
    "match_all":{}
    },

 "sort":{"age":{"order":"desc"}}
}

5,//前缀查询(prefix)(前缀是 wangwu的,
    比如 zhangsan wangwu is man(这个存的时候会进行分词),这个也会查出来)
GET /majian_index/user/_search
{
  "query":{
    "match_phrase_prefix": {
      "name": "wangwu"
    }
  }
}

6,//范围查询 (range)
参数 有  from,to,incluse_lower,include_upper,boost
include_lower是否包含左边界,默认true,
include_upper 是否包含右边界,默认true
(新版本的直接用 gte 和lte了?)

GET /majian_index/user/_search
{
  "query": {
    "range": {
      "age": {
        "gte": 10,
        "lte": 20
      }
    }
  }
}


7,通配符查询(wildcar 查询 *(0个或多个) 或?(一个字符),下面直接用 "name":"aaa*"这种格式也行)
GET /majian_index/user/_search
{
  "query":{
    "wildcard": {
      "name": {
        "value": "zhangsan*"
      }
    }
  }
}

8,模糊查询(fuzzy)

GET /majian_index/user/_search
{
  "query": {
    "fuzzy": {
      "name": "lisi"
    }
  }
}


9,filter查询(filter查询不计算相关度,可以缓存,速度快与query查询)
GET /majian_index/user/_search
{
  "query": {
    "bool": {
      "filter": {
        "term": {
          "name": "zhangsan"
        }
      }
    }
  }
}
//张三或李四
GET /majian_index/user/_search
{
  "query": {
    "bool": {
      "filter": {
        "terms": {
          "name": ["zhangsan","lisi"]
        }
      }
    }
  }
}

// 多个条件合再一起
GET /majian_index/user/_search
{
  "query": {
    "bool": {
      "filter": {
        "range": {
          "age": {
            "gte": 10,
            "lte": 30
          }
        }
      }
    }
  }
}

10,bool 查询 (must(sql 中and) should (sql中的or)  must_not (sql 中的 not))
(比如下面查的就是 age=30 或name="zhangsan"的,且 name !="lisi",也就是should里面是or 关系)
GET /majian_index/user/_search
{
  "query":{
    "bool": {
      "should": [
        {"term":{
          "age":30
        }},
        {
          "term": {
            "name":"zhangsan" 
          }
        }
      ],
      "must_not": [
        {"term":{
          "name":"lisi"
        }}
      ]
    }
  }
}

//里面还可以再嵌套bool
GET /majian_index/user/_search
{
  "query":{
    "bool": {
      "should": [
        {"term":{
          "age":30
        }},
        {
          "bool": {
            "must": [
              {"term": {
                "age":10
              }},
              {
                "term": {
                  "name":"zhangsan"
                }
              }
            ]
          }
        }
      ]
    }
  }
}

//查询 某个字段不为空的 (也就是sql 中的 is not null)(如下,查询字段age不为空的)

GET /majian_index/user/_search
{
  "query": {
    "bool": {
      "filter": {
        "exists": {
          "field": "age"
        }
      }
    }
  }
}


11.聚合查询(sql 中的 sum avage 等)
//下面的 aggs //是固定的表示聚合查询,sumage,是自己随便取的一个名字,用来存储查询结果
//这个会把结果和每一条都查出来(默认20条?),但是我们一般只关心结果,
//可以在aggs上面,加一个 size:0 字段,表示只要聚合查询的结果

GET /majian_index/user/_search
{
  "aggs":{
    "sumage":{
      "sum": {
        "field": "age"
      }
    }
  }
}

//cardinality (基数,像sql中的,分组后,有多少组)
GET /majian_index/user/_search
{
  "aggs":{
    "geshu":{
      "cardinality": {
        "field": "age"
      }
    }
  }
}

//分组  (相当于 sql中group by) 用terms 关键字(sss 同上面一样,自己随便
//取个名,来存结果)
GET /majian_index/user/_search
{
  "aggs": {
    "sss": {
      "terms": {
        "field": "age"
      }
    }
  },

"size": 0
}

//查询出名字是张三的,然后根据年龄分组,然后,查出每一组的平均值
// group_self,avg_self (同上面一样表示自己定义一个字段,用来存储,查询结果)

GET /majian_index/user/_search
{
  "query": {
    "match": {
      "name": "zhangsan"
    }
  },
  "aggs": {
    "group_self": {
      "terms": {
        "field": "age"
      },
      "aggs":{
        "avg_self":{
          "avg": {
            "field": "age"
          }
        }
      }
    }
  }
}

//同上面一样,查询出名字是张三的,然后根据年龄分组,然后,
//查出每一组的平均值,然后按平均值avg_self 降序排序

GET /majian_index/user/_search
{
  "query": {
    "match": {
      "name": "zhangsan"
    }
  },
  "aggs": {
    "group_self": {
      "terms": {
        "field": "age",
        "order": {
          "avg_self": "desc"
        }
      },
      "aggs":{
        "avg_self":{
          "avg": {
            "field": "age"
          }
        }
      }
    }
  }
}


四:通用

1,可以通过filter_path 来返回查询结果中的哪些字段

GET /afs_service3/user3/_search?q=*&filter_path=timed_out,took,hits.hits

2, es深度分页问题。
3,当对响应时间有有要求的时候后,可以加参数 timeout=10ms 等,返回已经查到的数据,

GET /majian_index/user/_search?timeout=10ms

4,可以通过explain=true,来查看如果计算相关度分数的

GET /majian_indx/user1/_search?explain=true

5,可以通过 GET/majian_index/user1/_explain?q=name:zhangsan 来查看 query子句的查询时否存在,不存在返回false,

6,docValues 是es为数字,和日期(非字符串)类型创建的,正排索引,对排序,分组,等一些聚合操作能

提升性能,默认是对不分词字段启用的,,对分词字段无效,(分词字段需要在mapping中把fielddata设置为true)

7,PUT /test/_doc/1?refresh (refresh 为空 或 refresh=true将会立即刷新,refresh=wait_for 将会等待刷新后返回,refresh=false 不会刷新,等待系统默认刷新
index.refresh_interval配置的默认值是1s)

22,字符串排序问题,用字符串排序的时候会出错,因为es会进行分词,索引字符串默认是不能排序的,如果想要排序,需要创建两个索引项,一个用于搜索,一个不分词,用于排序,,(注意下面的name字段中的fields,keyword表示不分词),还要把fielddata设置为true,这样设置后这个name字段即可以用于搜索,也可以用于排序了,但是如果在查询语句中直接使用 

"sort":[{"name":{"order":"desc"}}] 这样的话,排序是按照分词后的词进行排序的,应该在name后加个raw

也就是 "sort":[{"name.raw":{"order":"desc"}}] 这样就可以排序了(raw表示使用原始的文本进行排序)

PUT / majian_index1 /

    {   
        "settings": {      
            "index": {         
                "number_of_shards": 3,
                         "number_of_replicas": 0         
            }   
        },
           "mappings": {      
            "user3": {         
                "properties": {            
                    "name": {    
                        "type": "text",
                         "fields": {
                            "raw": {
                                "type": "keyword"
                            },
                           "fielddata":true
                        }                              
                    },
                      "age": {
                        "type": "long"
                    },
                      "content": {
                        "type": "text"
                    },
                      "date": {
                        "type": "date",
                        "index": false
                    }         
                }      
            }   
        }
    }

10,es copy_to 在创建索引的时候就要指定。比如 GET/majian_index/user/_serach?q=zhangsan,lisi

这个查询下没有字段名,只有字段值,es在查询时,会去每一个字段中去查找,zhangsan,或lisi(也 就是会分词?)

数据量大的时候效率很低,为此es提供了copy_to(可以把其他字段的值,链接到一起,查的时候就从这一个字段中查),

我们在创建mapping的时候要指定:如下(就会把name,content,复制到copy_fields字段上)  注意能被copy_to的字段必须是文本类型的

PUT /majian_index1/

{
    "settings":{
        "index":{
            "number_of_shards":3,
            "number_of_replicas":0
            }

    },
    "mappings":{
        "user3":{
            "properties":{
                "name":{"type":"text","copy_to":"copy_fields"},
                "age":{"type":"long"},

                "content":{"type":"text","copy_to":"copy_fields"},
                "date":{"type":"date","index":false}
            }
        }
    }
}

查询的时候  GET/majian_index1/user1/_search?q=copy_filelds:zhangsan,lisi  就会从copy_filelds

这个字段中去查询
11,GET twitter/_doc/1?stored_fields=tags,counter 通过 store 属性 ,来获取 store的字段,store为false的将会查不到

PUT twitter
{
"mappings": {
"_doc": {
"properties": {
"counter": {
"type": "integer",
"store": false
},
"tags": {
"type": "keyword",
"store": true
}
}
}
}
}


PUT twitter/_doc/1
{
"counter" : 1,
"tags" : ["red"]
}


12, HEAD /majian_index/user1/1  查看id为1 的文档是否存在

13, GET /majian_index/user1/1?realtime=false  (如果文档已经更新,但还没有刷新,get内部会调用 refresh,刷新数据,realtime改为false 将不刷新)

14,GET /afs_service1/user1/1?_source=false GET 默认会返回_source字段,可以通过 _source 设为false 不检索 _source字段

15,GET /afs_service1/user1/1?_source_include=age,name  可以通过(_source_include,_source_exclude 来包含或者排除某些字段(也可以直接用_source=name,age 来包含某些字段)
16,GET twitter/_doc/1/_source (直接返回source字段)
17,HEAD twitter/_doc/1/_source(测试source是否存在,比如创建mappingsd 使用禁用了_source将不会存原文档(会有这样一种场景比如source很大,我们
只需要检索,找到id,然后到hbase等其他数据源中再取具体内容))

18,GET twitter/_doc/2?routing=user1 存储和获取的时候可以指定路由字段,如果不指定路由字段默认会到所有分片查,然后聚合查询结果,如果指定了
路由字段只会查一个分片就行了,默认是 id做为路由。(如果mapping 中设置了_routing 再用id去查 比如GET twitter/_doc/2 就会出错,说没指定路由,id比较特殊?如果
GET twitter/_doc/_search?q=name:zhangsan 就可以,会查所有 分片,id字段特殊性的原因是啥?是由于在mapping 中设置了_routing 字段所以才会报错,如果不设置
的话就不会报错,但由于新增的时候指定了routing 根据id查询的时候不指定routing 会默认还按id routing,所以会找不到,所以根据id查的时候要强制指定routing)
也就是说如果maping 中设置了_routing 那么添加和按id查找的时候,就要指定routing,如果maping中没有设置 routing的话,单添加的时候指定了routing,按id
查找的时候,没有指定maping,那就会默认按id 路由,由于和添加的时候指定的路由不一致,会找不到,如果不按id查找,也不指定routing 就会到所有分片
上查结果,然后在聚合返回。如果不按id查找,但指定了routing,就只会到一个分片上去查,如果是添加的话,且mapping中设置了 routing ,那么添加也要带上
路由字段,否则会报错,查询不受影响 mapping 中的_routing 主要是为了防止添加的时候漏加routing,(see https://blog.csdn.net/u010454030/article/details/73554652/)
"mappings": {
"user1": {
"_routing": {
"required": true
},
"properties": {
"name": {
"type": "text"
},
"age": {
"type": "long"
},
"date": {
"type": "date",
"index": false
}
}
}
}


19,GET /afs_service1/user1/5?refresh=true (refresh设置为true 可以在查询前先刷新,注意,使用这个参数时,看看是否会造成系统负担)
20,分片查询 GET /afs_service1/user1/1?version=4&preference=_primary (指定只在主分片中查询,7.0中废弃只能用 [_only_nodes] or [_prefer_nodes])
如:GET /afs_service1/user1/1?version=4&preference=_only_nodes:node-1 在节点名为node-1的节点中查询

二:


1:es的数据类型

1,string,string 类型包含两种,text,和keyword,text 类型用来索引长文本,会进行分词,
而keyword,不会进行分词,keyword类型字段只能用本身来进行检索。
2,long,integer,short,byte,double,float,boolean,binary(二进制) 就是,如果我们给定的值是 true或false会自动检测成boolean 如果是字符串
会检测成string 如果是整数,会检测成 long,如果是小数,会检测成float
如果是 2018-12-12 会检测成date

3,数值类型不会进行分词,二字符串类型默认会进行分词,可以通过
GET /majian_index1/user1/_mapping 来查看mapping信息,

2:主分片,一旦确定,没法修改,replicas 可以修改


三:管理
1, 查看集群健康状况
GET _cat/health 

2,当集群中增加节点时,如果有replica 没创建,es 会自动创建

    

猜你喜欢

转载自www.cnblogs.com/dgwcxia/p/12028944.html
今日推荐