API 约定

编辑

Elasticsearch REST API 通过 HTTP 公开。除非另有说明,以下约定适用于所有 API。

Content-Type 要求

编辑

请求正文中发送的内容类型必须使用 Content-Type 标头指定。此标头的值必须映射到 API 支持的受支持格式之一。大多数 API 支持 JSON、YAML、CBOR 和 SMILE。批量和多搜索 API 支持 NDJSON、JSON 和 SMILE;其他类型将导致错误响应。

当使用 source 查询字符串参数时,必须使用 source_content_type 查询字符串参数指定内容类型。

Elasticsearch 仅支持 UTF-8 编码的 JSON。Elasticsearch 会忽略随请求发送的任何其他编码标头。响应也采用 UTF-8 编码。

X-Opaque-Id HTTP 标头

编辑

您可以传递 X-Opaque-Id HTTP 标头,以在 Elasticsearch 日志和任务中跟踪请求的来源。如果提供,Elasticsearch 会在以下位置显示 X-Opaque-Id 值:

对于弃用日志,Elasticsearch 还使用 X-Opaque-Id 值来限制和重复数据删除弃用警告。请参阅 弃用日志限制

X-Opaque-Id 标头接受任何任意值。但是,我们建议您将这些值限制为有限的集合,例如每个客户端一个 ID。不要为每个请求生成唯一的 X-Opaque-Id 标头。过多的唯一 X-Opaque-Id 值会阻止 Elasticsearch 在弃用日志中删除重复的警告。

traceparent HTTP 标头

编辑

Elasticsearch 还支持使用 官方 W3C 跟踪上下文规范traceparent HTTP 标头。您可以使用 traceparent 标头跨 Elastic 产品和其他服务跟踪请求。因为它仅用于跟踪,您可以安全地为每个请求生成唯一的 traceparent 标头。

如果提供,Elasticsearch 将在以下位置显示标头的 trace-id 值,作为 trace.id

例如,以下 traceparent 值将在上述日志中生成以下 trace.id 值。

`traceparent`: 00-0af7651916cd43dd8448eb211c80319c-b7ad6b7169203331-01
`trace.id`: 0af7651916cd43dd8448eb211c80319c

GET 和 POST 请求

编辑

许多 Elasticsearch GET API(最值得注意的是搜索 API)支持请求正文。虽然 GET 操作在检索信息的上下文中是有意义的,但并非所有 HTTP 库都支持带有正文的 GET 请求。所有需要正文的 Elasticsearch GET API 也可以作为 POST 请求提交。或者,您可以在使用 GET 时将请求正文作为 source 查询字符串参数传递。

Cron 表达式

编辑

cron 表达式是以下形式的字符串

    <seconds> <minutes> <hours> <day_of_month> <month> <day_of_week> [year]

Elasticsearch 使用 Quartz Job Scheduler 中的 cron 解析器。有关编写 Quartz cron 表达式的更多信息,请参阅 Quartz CronTrigger 教程

所有计划时间均为协调世界时 (UTC);不支持其他时区。

您可以使用 elasticsearch-croneval 命令行工具来验证您的 cron 表达式。

Cron 表达式元素

编辑

除了 year 之外,所有元素都是必需的。有关允许的特殊字符的信息,请参阅 Cron 特殊字符

<seconds>
(必需) 有效值:0-59 和特殊字符 , - * /
<minutes>
(必需) 有效值:0-59 和特殊字符 , - * /
<hours>
(必需) 有效值:0-23 和特殊字符 , - * /
<day_of_month>
(必需) 有效值:1-31 和特殊字符 , - * / ? L W
<month>
(必需) 有效值:1-12JAN-DECjan-dec 和特殊字符 , - * /
<day_of_week>
(必需) 有效值:1-7SUN-SATsun-sat 和特殊字符 , - * / ? L #
<year>
(可选) 有效值:1970-2099 和特殊字符 , - * /

Cron 特殊字符

编辑
*
选择字段的每个可能值。例如,hours 字段中的 * 表示“每小时”。
?
无特定值。当您不关心值是什么时使用。例如,如果您希望计划在每月的特定一天触发,但并不关心那天是星期几,则可以在 day_of_week 字段中指定 ?
-
一系列值(包括端点值)。用于分隔最小值和最大值。例如,如果您希望计划在上午 9:00 到下午 5:00 之间每小时触发一次,则可以在 hours 字段中指定 9-17
,
多个值。用于分隔字段的多个值。例如,如果您希望计划在每个星期二和星期四触发,则可以在 day_of_week 字段中指定 TUE,THU
/
递增。用于分隔指定时间递增时的值。第一个值表示起始点,第二个值表示间隔。例如,如果您希望计划从每小时开始每 20 分钟触发一次,则可以在 minutes 字段中指定 0/20。同样,在 day_of_month 字段中指定 1/5 将从每月的第一天开始每 5 天触发一次。
L
最后一个。在 day_of_month 字段中使用表示当月的最后一天 — 1 月为 31 日,非闰年 2 月为 28 日,4 月为 30 日,等等。在 day_of_week 字段中单独使用,代替 7SAT,或者在特定的一周中的某一天后使用,以选择该月中该类型的最后一天。例如,6L 表示该月的最后一个星期五。您可以在 day_of_month 字段中指定 LW 来指定该月的最后一个工作日。在指定值列表或范围时,请避免使用 L 选项,因为结果可能不会如您所愿。
W
工作日。用于指定最接近给定日期的工作日(星期一至星期五)。例如,如果在 day_of_month 字段中指定 15W,而 15 日是星期六,则计划将在 14 日触发。如果 15 日是星期日,则计划将在 16 日星期一触发。如果 15 日是星期二,则计划将在 15 日星期二触发。但是,如果指定 1W 作为 day_of_month 的值,而 1 日是星期六,则计划将在 3 日星期一触发 — 它不会跳过月份边界。您可以在 day_of_month 字段中指定 LW 来指定该月的最后一个工作日。只有当 day_of_month 是单日时,才能使用 W 选项 — 在指定天数范围或列表时无效。
#
一个月中的第 N 个 XXX 天。在 day_of_week 字段中使用,以指定该月的第 n 个 XXX 天。例如,如果您指定 6#1,则计划将在该月的第一个星期五触发。请注意,如果您指定 3#5,并且在特定月份中没有 5 个星期二,则该计划在该月份不会触发。

示例

编辑
设置每日触发器
编辑
0 5 9 * * ?
每天 UTC 时间上午 9:05 触发。
0 5 9 * * ? 2020
在 2020 年期间,每天 UTC 时间上午 9:05 触发。
将触发器限制在某一天或某个时间范围内
编辑
0 5 9 ? * MON-FRI
在周一至周五的 UTC 时间上午 9:05 触发。
0 0-5 9 * * ?
每天 UTC 时间上午 9:00 开始,到上午 9:05 结束,每分钟触发一次。
设置间隔触发器
编辑
0 0/15 9 * * ?
每天 UTC 时间上午 9:00 开始,到上午 9:45 结束,每 15 分钟触发一次。
0 5 9 1/3 * ?
从每月的第一天开始,每月每 3 天在 UTC 时间上午 9:05 触发。
设置在特定日期触发的计划
编辑
0 1 4 1 4 ?
每年 4 月 1 日 UTC 时间上午 4:01 触发。
0 0,30 9 ? 4 WED
在 4 月份的每个星期三,在 UTC 时间上午 9:00 和上午 9:30 触发。
0 5 9 15 * ?
每个月的 15 日在 UTC 时间上午 9:05 触发。
0 5 9 15W * ?
在每个月最接近 15 号的工作日上午 9:05 UTC 触发。
0 5 9 ? * 6#1
在每个月的第一个星期五上午 9:05 UTC 触发。
使用 last 设置触发器
编辑
0 5 9 L * ?
在每个月的最后一天上午 9:05 UTC 触发。
0 5 9 ? * 2L
在每个月的最后一个星期一上午 9:05 UTC 触发。
0 5 9 LW * ?
在每个月的最后一个工作日上午 9:05 UTC 触发。

索引和索引别名名称中的日期数学支持

编辑

日期数学名称解析允许您搜索时间序列索引或索引别名范围,而不是搜索所有索引并筛选结果。限制搜索的索引数量可以减少集群负载并提高搜索性能。例如,如果您要搜索每日日志中的错误,可以使用日期数学名称模板将搜索限制在过去两天内。

大多数接受索引或索引别名参数的 API 都支持日期数学。日期数学名称采用以下形式

<static_name{date_math_expr{date_format|time_zone}}>

其中

static_name

静态文本

date_math_expr

动态日期数学表达式,动态计算日期

date_format

可选格式,用于呈现计算出的日期。默认为 yyyy.MM.dd。格式应与 java-time https://docs.oracle.com/javase/8/docs/api/java/time/format/DateTimeFormatter.html 兼容

time_zone

可选时区。默认为 UTC

请注意 date_format 中使用的大小写字母。例如:mm 表示小时的分钟,而 MM 表示年份的月份。类似地,hh 表示与 AM/PM 结合使用的 1-12 范围的小时,而 HH 表示 0-23 24 小时范围内的小时。

日期数学表达式的解析与区域设置无关。因此,不可能使用格里高利历以外的任何其他日历。

您必须将日期数学名称括在尖括号中。如果您在请求路径中使用该名称,则特殊字符必须进行 URI 编码。例如

resp = client.indices.create(
    index="<my-index-{now/d}>",
)
print(resp)
response = client.indices.create(
  index: '<my-index-{now/d}>'
)
puts response
const response = await client.indices.create({
  index: "<my-index-{now/d}>",
});
console.log(response);
# PUT /<my-index-{now/d}>
PUT /%3Cmy-index-%7Bnow%2Fd%7D%3E

日期数学字符的百分比编码

用于日期舍入的特殊字符必须按如下方式进行 URI 编码

<

%3C

>

%3E

/

%2F

{

%7B

}

%7D

|

%7C

+

%2B

:

%3A

,

%2C

以下示例显示了日期数学名称的不同形式,以及在当前时间为 2024 年 3 月 22 日中午 UTC 时它们解析为的最终名称。

表达式 解析为

<logstash-{now/d}>

logstash-2024.03.22

<logstash-{now/M}>

logstash-2024.03.01

<logstash-{now/M{yyyy.MM}}>

logstash-2024.03

<logstash-{now/M-1M{yyyy.MM}}>

logstash-2024.02

<logstash-{now/d{yyyy.MM.dd|+12:00}}>

logstash-2024.03.23

要在名称模板的静态部分中使用字符 {},请使用反斜杠 \ 进行转义,例如

  • <elastic\{ON\}-{now/M}> 解析为 elastic{ON}-2024.03.01

以下示例显示了一个搜索请求,该请求搜索过去三天的 Logstash 索引,假设这些索引使用默认的 Logstash 索引名称格式 logstash-YYYY.MM.dd

$params = [
    'index' => '%3Clogstash-%7Bnow%2Fd-2d%7D%3E%2C%3Clogstash-%7Bnow%2Fd-1d%7D%3E%2C%3Clogstash-%7Bnow%2Fd%7D%3E',
    'body' => [
        'query' => [
            'match' => [
                'test' => 'data',
            ],
        ],
    ],
];
$response = $client->search($params);
resp = client.search(
    index="<logstash-{now/d-2d}>,<logstash-{now/d-1d}>,<logstash-{now/d}>",
    query={
        "match": {
            "test": "data"
        }
    },
)
print(resp)
response = client.search(
  index: '<logstash-{now/d-2d}>,<logstash-{now/d-1d}>,<logstash-{now/d}>',
  body: {
    query: {
      match: {
        test: 'data'
      }
    }
  }
)
puts response
res, err := es.Search(
	es.Search.WithIndex("%3Clogstash-%7Bnow%2Fd-2d%7D%3E%2C%3Clogstash-%7Bnow%2Fd-1d%7D%3E%2C%3Clogstash-%7Bnow%2Fd%7D%3E"),
	es.Search.WithBody(strings.NewReader(`{
	  "query": {
	    "match": {
	      "test": "data"
	    }
	  }
	}`)),
	es.Search.WithPretty(),
)
fmt.Println(res, err)
const response = await client.search({
  index: "<logstash-{now/d-2d}>,<logstash-{now/d-1d}>,<logstash-{now/d}>",
  query: {
    match: {
      test: "data",
    },
  },
});
console.log(response);
# 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"
    }
  }
}

多目标语法

编辑

大多数接受 <data-stream><index><target> 请求路径参数的 API 也支持多目标语法

在多目标语法中,您可以使用逗号分隔的列表在多个资源(例如数据流、索引或别名)上运行请求:test1,test2,test3。您还可以使用 类 glob 通配符 (*) 表达式来定位与模式匹配的资源:test**testte*t*test*

您可以使用 - 字符排除目标:test*,-test3

别名在通配符表达式之后解析。这可能导致请求定位到排除的别名。例如,如果 test3 是索引别名,则模式 test*,-test3 仍然定位到 test3 的索引。要避免这种情况,请改为排除别名的具体索引。

您还可以使用 - 字符从要搜索的集群列表中排除集群:remote*:*,-remote1:*,-remote4:* 将搜索别名以“remote”开头的所有集群,但“remote1”和“remote4”除外。请注意,要使用此表示法排除集群,您必须排除其所有索引。目前不支持排除远程集群上索引的子集。例如,这将引发异常:remote*:*,-remote1:logs*

可以定位索引的多目标 API 支持以下查询字符串参数

ignore_unavailable
(可选,布尔值)如果为 false,则如果请求定位到丢失或关闭的索引,则会返回错误。默认为 false
allow_no_indices
(可选,布尔值)如果为 false,则如果任何通配符表达式、索引别名_all 值仅定位到丢失或关闭的索引,则会返回错误。即使请求定位到其他打开的索引,此行为也适用。例如,如果索引以 foo 开头,但没有索引以 bar 开头,则定位到 foo*,bar* 的请求会返回错误。
expand_wildcards

(可选,字符串)通配符模式可以匹配的索引类型。如果请求可以定位数据流,则此参数确定通配符表达式是否匹配隐藏的数据流。支持逗号分隔的值,例如 open,hidden。有效值为

all
匹配任何数据流或索引,包括隐藏的数据流或索引。
open
匹配打开的、非隐藏的索引。也匹配任何非隐藏的数据流。
closed
匹配关闭的、非隐藏的索引。也匹配任何非隐藏的数据流。数据流无法关闭。
hidden
匹配隐藏的数据流和隐藏的索引。必须与 openclosed 或两者结合使用。
none
不接受通配符模式。

以上参数的默认设置取决于正在使用的 API。

一些可以定位索引的多目标 API 还支持以下查询字符串参数

ignore_throttled

(可选,布尔值)如果为 true,则在冻结时会忽略具体、展开或别名的索引。默认为 true

[7.16.0] 在 7.16.0 中已弃用。

具有单个目标的 API(例如获取文档 API)不支持多目标语法。

隐藏的数据流和索引

编辑

对于大多数 API,通配符表达式默认不匹配隐藏的数据流和索引。要使用通配符表达式匹配隐藏的数据流和索引,必须指定 expand_wildcards 查询参数。

或者,查询以点开头的索引模式(例如 .watcher_hist*)默认会匹配隐藏的索引。这旨在镜像 Unix 文件 globbing 行为,并为隐藏索引提供更平滑的过渡路径。

您可以通过在数据流的匹配索引模板中将 data_stream.hidden 设置为 true 来创建隐藏的数据流。您可以使用 index.hidden 索引设置来隐藏索引。

数据流的后备索引会自动隐藏。某些功能(例如机器学习)将信息存储在隐藏的索引中。

与所有索引匹配的全局索引模板不会应用于隐藏的索引。

系统索引

编辑

Elasticsearch 模块和插件可以将配置和状态信息存储在内部系统索引中。您不应直接访问或修改系统索引,因为它们包含对系统运行至关重要的数据。

直接访问系统索引已弃用,并且在未来的主要版本中将不再允许。

参数

编辑

REST 参数(使用 HTTP 时,映射到 HTTP URL 参数)遵循使用下划线大小写的约定。

查询字符串中的请求正文

编辑

对于不接受非 POST 请求的请求正文的库,您可以改为将请求正文作为 source 查询字符串参数传递。使用此方法时,还应传递 source_content_type 参数,并使用指示源格式的媒体类型值,例如 application/json

REST API 版本兼容性

编辑

主要版本升级通常包含许多破坏性更改,这些更改会影响您与 Elasticsearch 的交互方式。虽然我们建议您在升级 Elasticsearch 之前监视弃用日志并更新应用程序,但协调必要的更改可能会成为升级的障碍。

您可以通过包含 API 兼容性标头来启用现有应用程序在升级后无需修改即可运行,这些标头会告知 Elasticsearch 您仍在使用的以前版本的 REST API。使用这些标头可使请求和响应的结构保持不变;它不保证相同的行为。

您可以在 Content-TypeAccept 标头中按每个请求设置版本兼容性。将 compatible-with 设置为您正在运行的版本相同的版本没有影响,但可以确保在升级 Elasticsearch 后请求仍然有效。

要告诉 Elasticsearch 8.0 您正在使用 7.x 请求和响应格式,请设置 compatible-with=7

Content-Type: application/vnd.elasticsearch+json; compatible-with=7
Accept: application/vnd.elasticsearch+json; compatible-with=7

HTTP 429 Too Many Requests 状态代码回退

编辑

Elasticsearch API 可能会响应 HTTP 429 Too Many Requests 状态代码,表示集群太忙而无法处理请求。发生这种情况时,请考虑在短暂延迟后重试。如果重试也收到 429 Too Many Requests 响应,请在每次后续重试之前通过指数回退来延长延迟。

基于 URL 的访问控制

编辑

许多用户使用带有基于 URL 的访问控制的代理来保护对 Elasticsearch 数据流和索引的访问。对于 多搜索多获取批量请求,用户可以选择在 URL 中和请求正文内的每个单独请求中指定数据流或索引。这可能会使基于 URL 的访问控制具有挑战性。

为了防止用户覆盖 URL 中指定的数据流或索引,请在 elasticsearch.yml 中将 rest.action.multi.allow_explicit_index 设置为 false

这将导致 Elasticsearch 拒绝在请求正文中显式指定数据流或索引的请求。

布尔值

编辑

所有 REST API 参数(包括请求参数和 JSON 正文)都支持提供布尔值 “false” 作为值 false 和布尔值 “true” 作为值 true。所有其他值都会引发错误。

数值

编辑

在请求正文中传递数字参数时,您可以使用包含该数字的 string 而不是本机数字类型。例如

resp = client.search(
    size="1000",
)
print(resp)
response = client.search(
  body: {
    size: '1000'
  }
)
puts response
const response = await client.search({
  size: 1000,
});
console.log(response);
POST /_search
{
  "size": "1000"
}

响应体中的整数值字段在本手册中被描述为 integer(或偶尔为 long),但通常对这些值没有明确的界限。JSON、SMILE、CBOR 和 YAML 都允许任意大的整数值。不要假设响应体中的 integer 字段始终适合 32 位有符号整数。

字节大小单位

编辑

当需要指定数据字节大小时,例如设置缓冲区大小参数时,该值必须指定单位,例如 10 千字节用 10kb 表示。请注意,这些单位使用 1024 的幂,因此 1kb 表示 1024 字节。支持的单位有:

b

字节

kb

千字节

mb

兆字节

gb

千兆字节

tb

太字节

pb

拍字节

距离单位

编辑

在需要指定距离的地方,例如 地理距离查询中的 distance 参数,如果未指定单位,则默认单位为米。距离可以使用其他单位指定,例如 "1km""2mi"(2 英里)。

以下是完整的单位列表

英里

mimiles

ydyards

英尺

ftfeet

英寸

ininch

千米

kmkilometers

mmeters

厘米

cmcentimeters

毫米

mmmillimeters

海里

NM, nmi, 或 nauticalmiles

时间单位

编辑

当需要指定持续时间时,例如 timeout 参数,持续时间必须指定单位,例如 2 天用 2d 表示。支持的单位有:

d

h

小时

m

分钟

s

ms

毫秒

micros

微秒

nanos

纳秒

无单位数量

编辑

无单位数量意味着它们没有像“字节”、“赫兹”、“米”或“长吨”这样的“单位”。

如果其中一个数量很大,我们会将其打印为 10m 表示 10,000,000,或 7k 表示 7,000。但当我们指的是 87 时,我们仍然会打印 87。以下是支持的乘数:

k

m

g

t

p