8. ES API规约
8.1 多索引
通常可以用test1、test2、test3这样的形式(或者用_all表示所有索引),当然它也支持通配符(如:test*、*test或者te*t),排除某些索引可以用-符号,比如test*,-test3(匹配所有的test开头的索引但不包括test3),所有的多索引API都支持下面的url查询字符串参数:
ignore_unavailable:如果指定索引不存在或者是封闭索引,这个参数可以控制这些索引是否可以被忽略,可以指定为true或false;allow_no_indices:如果通配符索引表达式没有匹配到具体索引,这个参数可以控制是否失败,可以指定为true或false,不如foo*,但是却没有以foo开头的索引,据此可以设置为失败,这个参数同样适用于_all、*或者像test这样具体的某个索引,如果一个别名指向封闭索引,则此设置也适用于别名;expand_wildcards:控制通配符索引表达式可以匹配到哪种具体索引,如果指定了open,则通配符表达式只能匹配到打开的索引,如果指定了closed,则通配符表达式仅能匹配到封闭的索引,它还能同时指定为open和closed两个值。
8.2 索引名对日期和数学的支持
日期、数学索引名称解析可以让我们搜索一系列时间序列索引,而不是搜索所有时间序列索引并过滤结果或维护别名。限制搜索的索引数可以减少集群上的负载并提高执行性能。比如,在日志中搜索错误,就可以使用日期、数学名称模板将搜索限制为过去两天。几乎所有的API都有index参数,index参数可以支持日期和数学,大概的格式如下:
<static_name{date_math_expr{date_format|time_zone}}>
对上述的语句中的几个参数做如下说明:
static_name:名称的静态文本部分;date_math_expr:动态日期、数学数学表达式(动态计算日期);date_format:呈现计算日期的格式(可选),默认是YYYY.MM.dd格式;time_zone:时区(可选),默认是UTC。
下面是一个简单的例子:
# GET /<logstash-{now/d}>/_search
GET /%3Clogstash-%7Bnow%2Fd%7D%3E/_search
{
"query" : {
"match": {
"test": "data"
}
}
}
【注意】
日期数学索引名称表达式必须包在尖括号中,并且所有特殊字符都应该是URI编码的,下面是具体的参照表:
| 特殊字符 | URI编码 |
|---|---|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
下面是对2024年3月22日中午(UTC)不同参数对应的解析结果:
| 表达式 | 解析结果 |
|---|---|
|
|
|
|
|
|
|
|
|
|
【注意】如果要在索引名称模板的静态部分中使用字符{和},需要用反斜杠\来转义,如:
<elastic\\{ON\\}-{now/M}>解析为elastic{ON}-2024.03.01
以下示例显示搜索请求,该搜索请求搜索过去三天的Logstash索引,假设索引使用默认的Logstash索引名称格式logstash-YYYY.MM.dd,那么如下:
# GET /<logstash-{now/d-2d}>,<logstash-{now/d-1d}>,<logstash-{now/d}>/_search
GET /%3Clogstash-%7Bnow%2Fd-2d%7D%3E%2C%3Clogstash-%7Bnow%2Fd-1d%7D%3E%2C%3Clogstash-%7Bnow%2Fd%7D%3E/_search
{
"query" : {
"match": {
"test": "data"
}
}
}
8.3 常规选项
下面的这些选项适用于所有的REST APIs,不局限于ES。
8.3.1 美化返回结果
之前有提过这个参数,可以在任何请求后面追加?pretty=true,任何JSON格式的返回结果都将会被格式化(美化),一般只在调试的时候使用!另一个相类似的是?format=yaml参数可以返回更加易读的yaml格式的结果。
8.3.2 更易阅读的输出
有些返回结果更适用于人(如"exists_time": "1h"和"size": "1kb"),有些返回结形式则更适合机器(如"exists_time_in_millis": 3600000和"size_in_bytes": 1024),适合人的阅读方式在请求时追加?human=false将其关闭,当统计结果被监控工具(机器)消耗时,这是有意义的,而不是用于人类消费,这个选项默认是flase。
8.3.3 日期数字
大部分接受格式化日期值参数都是能解析日期数值的,比如range查询中的gt和lt以及daterange聚合中的from和to。它可以是任意的固定好的日期(原文是anchor date),可以是now或者以||结尾的日期字符串,除此之外固定日期后面可以跟下面的一个或多个表达式:
+1h:加1小时;-1d:减1小时;/d:四舍五入到最近的一天;
ES支持的时间单位也和持续时间的单位也有点不太一样,ES只支持年(y)月(M)日(d)周(w)时(H)分(m)秒(s),下面有2个案例(假设当前时间为2001-01-01 12:00:00):
now-1h/d解析结果为2001-01-01 00:00:00;2001.02.01\|\|+1M/d解析结果为2001-03-01 00:00:00;
8.3.4 过滤返回结果
所有的REST APIS都可以接受一个减少ES返回值的过滤参数filter_path,这个参数接受一系列使用.表示的过滤器(多个过滤器之间使用,分隔),比如:
GET /_search?q=elasticsearch&filter_path=took,_shards.total,hits
看结果:
{
"took": 3,
"_shards": {
"total": 15
},
"hits": {
"total": 0,
"max_score": null,
"hits": []
}
}
直接将took、_shards.total和hits这三块过滤出来然后将过滤的东西返回给我们,注意这里不是将指定的filter_path过滤掉,而是将它显示出来(总感觉这里“过滤”这个词用的怪怪的,对吧),filter_path也是可以使用通配符*匹配任何字段或者字段名的一部分,比如下面的:
GET /_cluster/state?filter_path=metadata.indices.*.stat*
返回的结果如下:
{
"metadata": {
"indices": {
".kibana": {
"state": "open"
},
".monitoring-kibana-6-2018.09.06": {
"state": "open"
},
".monitoring-kibana-6-2018.09.05": {
"state": "open"
},
".monitoring-es-6-2018.09.05": {
"state": "open"
},
"bank": {
"state": "open"
},
"customer": {
"state": "open"
},
".monitoring-es-6-2018.09.06": {
"state": "open"
}
}
}
}
另外**通配符可用于包括字段而不知道字段的确切路径的匹配,比如使用请求返回每个片段的Lucene版本:
GET /_cluster/state?filter_path=routing_table.indices.**.state
在过滤的时候也可以使用-符号来排除一些东西,如排除掉命中结果:
GET /_search?q=elasticsearch&filter_path=-hits
为了过滤复杂条件,包含和排他过滤器可以组合在同一表达式中。在这种情况下,将首先应用排他过滤器,并使用包含过滤器再次过滤结果:
GET /_cluster/state?filter_path=metadata.indices.*.state,-metadata.indices.logstash-*
8.3.5 标识设置
这个参数(默认为false)主要用于获取设置参数的返回形式,当flat_settings=true时,设置将以平面格式(flat format)的返回,比如下面的:
GET twitter/_settings?flat_settings=true
// 结果如下
{
"twitter" : {
"settings": {
"index.number_of_replicas": "1",
"index.number_of_shards": "1",
"index.creation_date": "1474389951325",
"index.uuid": "n6gzFZTgS664GUfx0Xrpjw",
"index.version.created": ...,
"index.provided_name" : "twitter"
}
}
}
当flat_settings=false时,设置将会以更加人类可读的形式返回:
GET twitter/_settings?flat_settings=false
// 结果如下
{
"twitter" : {
"settings" : {
"index" : {
"number_of_replicas": "1",
"number_of_shards": "1",
"creation_date": "1474389951325",
"uuid": "n6gzFZTgS664GUfx0Xrpjw",
"version": {
"created": ...
},
"provided_name" : "twitter"
}
}
}
}
8.3.6 关于一些单位
时间单位:
对于持续性时间(比如超时时间timeout参数)必须指定单位,ES支持的时间单位如下:
| 天 |
| 小时 |
| 分钟 |
| 秒 |
| 毫秒 |
| 微秒 |
| 纳秒 |
数据字节单位:
对于数据字节大小必须要指定,比如在设置缓冲区大小。注意,这些单位都是使用1024的幂,即1kb=1024b(复杂化了……),主要就单位有:
| 字节 |
| 千字节 |
| 兆字节 |
| 千兆字节 |
| T |
| P |
无单位数的单位:
即没有像“字节”或“赫兹”或“米”或“长吨”这样的“单位”,如果这些数很大,打印的时候就用10m代替10,000、用7k代替7,000,而87仍会打印87,主要支持的单位有:
`` | Single |
| Kilo |
| Mega |
| Giga |
| Tera |
| Peta |
距离单位:
即距离单位,比如使用distance参数时,支持的单位有:
英里 |
|
码 |
|
英尺 |
|
英寸 |
|
公里 |
|
米 |
|
厘米 |
|
毫米 |
|
海里 |
|
8.3.7 基于一个URL的访问控制
许多用户使用代理和基于url的访问控制安全访问Elasticsearch索引,多搜索、多获取和批处理请求,用户可以在URL请求体中指定索引的选择和每个请求,使得基于URL的访问控制面对挑战,为了避免用户在URL已经指定的索引,需要在elasticsearch.yml文件中添加如下配置:rest.action.multi.allow_explicit_index: false,这个配置的默认值是true,但是设置为false,ES将不会接受请求体中带指定索引的请求。