为了方便其他语言的整合Elasticsearch为开发者提供了一套基于Http协议的Restful接口,只需要构造rest请求并解析请求返回的json即可实现访问Elasticsearch服务器。Elasticsearch的API接口功能丰富,包含集群、监控、部署管理等,也包含常用的文档、索引操作。
REST API - 很容易被各种语言调用
文档的操作
操作 | REST API | 参数 |
---|---|---|
Index | PUT my_index/_doc/1 | {"user":"mike","comment":"You Konw,for search"} |
Create | PUT my_index/_create/1 POST my_index/_doc(不指定ID,自动生成) |
{"user":"mike","comment":"You Konw,for search"} {"user":"mike","comment":"You Konw,for search"} |
Read | GET my_index/_doc/1 | |
Update | POST my_index/_update/1 | {"doc":{"user":"mike","comment":"You Konw,for search"}} |
Delete | DELETE my_index/_doc/1 |
- Type 名,约定都用
_doc
- Create - 如果ID已经存在,会失败
- Index - 如果 ID 不存在 ,创建新的文档。否则,先删除现有的文档,再创建新的文档,版本会增加
- Update -文档必须已经存在,更新只会对相应字段做增量修改
Create 一个文档
指定文档ID
PUT users/_create/1
{
"firstName":"Jack",
"lastName":"Johnson",
"tags":["guitar","skateboard"]
}
or # 手动设置 type 是 create
PUT users/_doc/1?op_type=create
{
"firstName":"Jack",
"lastName":"Johnson",
"tags":["guitar","skateboard"]
}
返回结果:
{
"_index" : "users",
"_type" : "_doc",
"_id" : "1", # 手动指定的文档编号
"_version" : 1,
"result" : "created",
"_shards" : {
"total" : 2,
"successful" : 1,
"failed" : 0
},
"_seq_no" : 0,
"_primary_term" : 1
}
如果已经存在会报错:
{
"error": {
"root_cause": [
{
"type": "version_conflict_engine_exception",
"reason": "[1]: version conflict, document already exists (current version [1])",
"index_uuid": "nzRRiahvRtSNNSf7oohKEQ",
"shard": "0",
"index": "users"
}
],
"type": "version_conflict_engine_exception",
"reason": "[1]: version conflict, document already exists (current version [1])",
"index_uuid": "nzRRiahvRtSNNSf7oohKEQ",
"shard": "0",
"index": "users"
},
"status": 409
}
自动生成ID
POST users/_doc
{
"firstName":"Tom",
"lastName":"Jerry",
"tags":["cat","rat"]
}
返回结果:
{
"_index" : "users",
"_type" : "_doc",
"_id" : "VWsV9WwBOKERAIDEZ-sc", # 自动生成的文档编号
"_version" : 1,
"result" : "created",
"_shards" : {
"total" : 2,
"successful" : 1,
"failed" : 0
},
"_seq_no" : 1,
"_primary_term" : 1
}
Get 一个文档
找到文档,返回 HTTP 200
- 文档元信息
- _index/_type/
- 版本信息,同一个ID的文档 即使被删除 Version号也会不断增加
- source 中默认包含了 文档的所有原始信息
GET users/_doc/1
返回结果
{
"_index" : "users", # 索引名称
"_type" : "_doc", # type
"_id" : "1", # 主键
"_version" : 1, # 版本
"_seq_no" : 0,
"_primary_term" : 1,
"found" : true,
"_source" : { # 原始信息
"firstName" : "Jack",
"lastName" : "Johnson",
"tags" : [
"guitar",
"skateboard"
]
}
}
找不到文档,返回HTTP 404
GET users/_doc/2
返回结果:
{
"_index" : "users",
"_type" : "_doc",
"_id" : "2",
"found" : false
}
Index(索引) 文档
Index 和Create 不一样的地方: 如果文档不存在,就索引新的文档。否则现有文档会被删除,新的文档被索引。版本信息+1;
put 文档
PUT users/_doc/1
{
"tags":["guitar","skateboard","reading"]
}
返回结果:
{
"_index" : "users",
"_type" : "_doc",
"_id" : "1",
"_version" : 2,
"result" : "updated",
"_shards" : {
"total" : 2,
"successful" : 1,
"failed" : 0
},
"_seq_no" : 2,
"_primary_term" : 1
}
获取操作后的文档
GET users/_doc/1
返回结果:
{
"_index" : "users",
"_type" : "_doc",
"_id" : "1",
"_version" : 2,
"_seq_no" : 2,
"_primary_term" : 1,
"found" : true,
"_source" : {
"tags" : [
"guitar",
"skateboard",
"reading"
]
}
}
Update 文档
- Update方法不会删除原来的文档,而是实现真正的数据更新
- Post方法 / Payload 需要包含在
doc
中
更新文档
POST users/_update/1
{
"doc":{
"albums":["album1","album2"]
}
}
返回结果:
{
"_index" : "users",
"_type" : "_doc",
"_id" : "1",
"_version" : 3,
"result" : "updated",
"_shards" : {
"total" : 2,
"successful" : 1,
"failed" : 0
},
"_seq_no" : 3,
"_primary_term" : 1
}
获取更新后的文档
GET users/_doc/1
返回结果:
{
"_index" : "users",
"_type" : "_doc",
"_id" : "1",
"_version" : 3,
"_seq_no" : 3,
"_primary_term" : 1,
"found" : true,
"_source" : {
"tags" : [
"guitar",
"skateboard",
"reading"
],
"albums" : [
"album1",
"album2"
]
}
}
put 和 update 的区别
- update 会将数据更新,未修改的字段保持愿值
- put 会直接覆盖掉元数据(元数据删除掉后,重新索引)
delete 文档
DELETE users/_doc/1
返回结果:
{
"_index" : "users",
"_type" : "_doc",
"_id" : "1",
"_version" : 7,
"result" : "deleted",
"_shards" : {
"total" : 2,
"successful" : 1,
"failed" : 0
},
"_seq_no" : 7,
"_primary_term" : 3
}
Indices
创建索引
PUT movies
返回结果:
{
"acknowledged" : true,
"shards_acknowledged" : true,
"index" : "movies"
}
删除索引
DELETE movies
返回结果:
{
"acknowledged" : true
}
批量操作
Bulk API
在一个REST请求的时候,重新建立网络开销是非常损耗性能的,Bulk API的核心思想就是,在一次请求中,做不同的操作。
- 支持在一次API 调用中,对不同对索引进行操作
- 支持四种类型操作
- Index
- Create
- Update
- Delete
- 可以在URI中指定Index,也可以在请求的Payload中进行
- 操作中单条操作失败,并不会影响其他操作
- 返回结果包括了每一条操作执行的结果
Demo
请求:
POST _bulk # 这个是请求地址
# 索引一个文档 指明索引是test 文档编号(主键)是 1 字段名为 field1 值为 value1
{"index":{"_index":"test","_id":"1"}}
{"field1":"value1"}
# 删除 一个文档 指明索引是 test 文档编号(主键)是2
{"delete":{"_index":"test","_id":"2"}}
# 创建一个文档,指明索引是test2 文档编号(主键)是 3 字段名为 field1 值为 value3
{"create":{"_index":"test2","_id":"3"}}
{"field1":"value3"}
# 更新一个文档 指明索引是test 文档编号(主键)是1 修改的字段是 field2 值为 value2
{"update":{"_index":"test","_id":"1"}}
{"doc": {"field2":"value2"}}
返回结果:
{
"took" : 288,
"errors" : false,
"items" : [
# 第一个操作的返回值 创建成功,HTTP响应 201
{
"index" : {
"_index" : "test",
"_type" : "_doc",
"_id" : "1",
"_version" : 1,
"result" : "created", # 创建成功
"_shards" : {
"total" : 2,
"successful" : 1,
"failed" : 0
},
"_seq_no" : 0,
"_primary_term" : 1,
"status" : 201 # HTTP响应码
}
},
# 第二个操作的返回值 删除失败,HTTP响应 404
{
"delete" : {
"_index" : "test",
"_type" : "_doc",
"_id" : "2",
"_version" : 1,
"result" : "not_found", # 文档不存在
"_shards" : {
"total" : 2,
"successful" : 1,
"failed" : 0
},
"_seq_no" : 1,
"_primary_term" : 1,
"status" : 404 # HTTP响应码
}
},
# 第三个操作的返回值 创建成功,HTTP响应 201
{
"create" : {
"_index" : "test2",
"_type" : "_doc",
"_id" : "3",
"_version" : 1,
"result" : "created", # 创建成功
"_shards" : {
"total" : 2,
"successful" : 1,
"failed" : 0
},
"_seq_no" : 0,
"_primary_term" : 1,
"status" : 201 # HTTP响应码
}
},
# 第四个操作的返回值 更新成功,HTTP响应 200
{
"update" : {
"_index" : "test",
"_type" : "_doc",
"_id" : "1",
"_version" : 2,
"result" : "updated", # 更新成功
"_shards" : {
"total" : 2,
"successful" : 1,
"failed" : 0
},
"_seq_no" : 2,
"_primary_term" : 1,
"status" : 200 # HTTP响应码
}
}
]
}
mget 批量读取
批量读取可以减少网络连接锁产生的开销。提高性能
Demo
请求:
GET _mget
{
"docs":[
{
"_index":"test",
"_id":1
},
{
"_index":"test2",
"_id":1
}
]
}
返回结果:
{
"docs" : [
{
"_index" : "test",
"_type" : "_doc",
"_id" : "1",
"_version" : 2,
"_seq_no" : 2,
"_primary_term" : 1,
"found" : true,
"_source" : {
"field1" : "value1",
"field2" : "value2"
}
},
{
"_index" : "test2",
"_type" : "_doc",
"_id" : "1",
"found" : false //未找到 只有id为3的没有id为1的
}
]
}
msearch 批量查询
Demo
请求:
POST test/_msearch //在 test 索引上查查询
{}
{"query":{"match_all":{}},"size":1} // 查询所有,只返回一条
{"index":"test2"} //可以指定其他的索引,这个是 test2索引
{"query":{"match_all":{}},"size":1}
返回结果:
{
"took" : 9,
"responses" : [
{
"took" : 2,
"timed_out" : false,
"_shards" : {
"total" : 1,
"successful" : 1,
"skipped" : 0,
"failed" : 0
},
"hits" : {
"total" : {
"value" : 1,
"relation" : "eq"
},
"max_score" : 1.0,
"hits" : [
{
"_index" : "test",
"_type" : "_doc",
"_id" : "1",
"_score" : 1.0,
"_source" : {
"field1" : "value1",
"field2" : "value2"
}
}
]
},
"status" : 200
},
{
"took" : 1,
"timed_out" : false,
"_shards" : {
"total" : 1,
"successful" : 1,
"skipped" : 0,
"failed" : 0
},
"hits" : {
"total" : {
"value" : 1,
"relation" : "eq"
},
"max_score" : 1.0,
"hits" : [
{
"_index" : "test2",
"_type" : "_doc",
"_id" : "3",
"_score" : 1.0,
"_source" : {
"field1" : "value3"
}
}
]
},
"status" : 200
}
]
}
常见错误返回
问题 | 原因 |
---|---|
无法连接 | 网络故障或集群挂了 |
连接无法关闭 | 网络故障或节点出错 |
429 | 集群过于繁忙 |
4xx | 请求体格式有错 |
500 | 集群内部错误 |