S3 存储库
编辑S3 存储库
编辑您可以将 AWS S3 用作 快照/恢复 的存储库。
如果您正在寻找 AWS 上托管的 Elasticsearch 解决方案,请访问 https://elastic.ac.cn/cloud/。
请观看 此视频,了解如何连接 AWS S3 存储库的演练。
入门
编辑要注册 S3 存储库,请在创建存储库时将类型指定为 s3
。存储库默认使用 ECS IAM 角色凭据进行身份验证。您还可以使用 Kubernetes 服务帐户进行身份验证。
唯一强制设置是存储桶名称
resp = client.snapshot.create_repository( name="my_s3_repository", repository={ "type": "s3", "settings": { "bucket": "my-bucket" } }, ) print(resp)
const response = await client.snapshot.createRepository({ name: "my_s3_repository", repository: { type: "s3", settings: { bucket: "my-bucket", }, }, }); console.log(response);
PUT _snapshot/my_s3_repository { "type": "s3", "settings": { "bucket": "my-bucket" } }
客户端设置
编辑您用于连接到 S3 的客户端有许多可用设置。这些设置的形式为 s3.client.CLIENT_NAME.SETTING_NAME
。默认情况下,s3
存储库使用名为 default
的客户端,但可以使用 存储库设置 client
修改此设置。例如
resp = client.snapshot.create_repository( name="my_s3_repository", repository={ "type": "s3", "settings": { "bucket": "my-bucket", "client": "my-alternate-client" } }, ) print(resp)
const response = await client.snapshot.createRepository({ name: "my_s3_repository", repository: { type: "s3", settings: { bucket: "my-bucket", client: "my-alternate-client", }, }, }); console.log(response);
PUT _snapshot/my_s3_repository { "type": "s3", "settings": { "bucket": "my-bucket", "client": "my-alternate-client" } }
大多数客户端设置可以添加到 elasticsearch.yml
配置文件中,但安全设置除外,您需要将其添加到 Elasticsearch 密钥库中。有关创建和更新 Elasticsearch 密钥库的更多信息,请参阅 安全设置。
例如,如果您想使用特定的凭据访问 S3,请运行以下命令将这些凭据添加到密钥库。
bin/elasticsearch-keystore add s3.client.default.access_key bin/elasticsearch-keystore add s3.client.default.secret_key # a session token is optional so the following command may not be needed bin/elasticsearch-keystore add s3.client.default.session_token
如果您希望使用实例角色或容器角色访问 S3,则应将这些设置保持未设置状态。您可以通过从密钥库中删除这些设置来从使用特定凭据切换回使用实例角色或容器角色的默认设置,如下所示
bin/elasticsearch-keystore remove s3.client.default.access_key bin/elasticsearch-keystore remove s3.client.default.secret_key # a session token is optional so the following command may not be needed bin/elasticsearch-keystore remove s3.client.default.session_token
此存储库类型的所有客户端安全设置都是可重新加载的。您可以在节点启动前定义这些设置,或者在定义设置后调用节点重新加载安全设置 API,以将其应用于正在运行的节点。
重新加载设置后,用于传输快照内容的内部 s3
客户端将使用密钥库中的最新设置。任何现有的 s3
存储库以及任何新创建的存储库都将获取密钥库中存储的新值。
正在进行的快照/恢复任务不会被客户端安全设置的重新加载抢占。任务将使用操作启动时构建的客户端完成。
以下列表包含可用的客户端设置。必须存储在密钥库中的设置标记为“安全”且可重新加载;其他设置属于 elasticsearch.yml
文件。
-
access_key
(安全,可重新加载) - S3 访问密钥。如果设置,还必须指定
secret_key
设置。如果未设置,客户端将改为使用实例或容器角色。 -
secret_key
(安全,可重新加载) - S3 密钥。如果设置,还必须指定
access_key
设置。 -
session_token
(安全,可重新加载) - S3 会话令牌。如果设置,还必须指定
access_key
和secret_key
设置。 -
endpoint
- 要连接的 S3 服务端点。这默认为
s3.amazonaws.com
,但 AWS 文档列出了备选的 S3 端点。如果您正在使用与 S3 兼容的服务,则应将其设置为该服务的端点。 -
protocol
- 用于连接到 S3 的协议。有效值是
http
或https
。默认为https
。使用 HTTPS 时,此存储库类型会使用 JVM 范围内的信任库验证存储库的证书链。使用 JVM 的keytool
工具确保根证书颁发机构在此信任库中。如果您为 S3 存储库使用自定义证书颁发机构,并且使用 Elasticsearch 捆绑的 JDK,则每次升级 Elasticsearch 时都需要重新安装 CA 证书。 -
proxy.host
- 用于通过其连接到 S3 的代理的主机名。
-
proxy.port
- 用于通过其连接到 S3 的代理的端口。
-
proxy.scheme
- 用于与 S3 的代理连接的方案。有效值是
http
或https
。默认为http
。此设置允许指定用于与代理服务器通信的协议 -
proxy.username
(安全,可重新加载) - 用于连接到
proxy.host
的用户名。 -
proxy.password
(安全,可重新加载) - 用于连接到
proxy.host
的密码。 -
read_timeout
- (时间值) Elasticsearch 在关闭与存储库的已建立的打开连接之前,等待接收连接下一个字节数据的最长时间。默认值为 50 秒。
-
max_connections
- 与 S3 的最大并发连接数。默认值为
50
。 -
max_retries
- S3 请求失败时要使用的重试次数。默认值为
3
。 -
use_throttle_retries
- 是否应限制重试(即应退避)。必须为
true
或false
。默认为true
。 -
path_style_access
- 是否强制使用路径样式访问模式。如果为
true
,将使用路径样式访问模式。如果为false
,访问模式将由 AWS Java SDK 自动确定(有关详细信息,请参阅 AWS 文档)。默认为false
。
在 7.0
、7.1
、7.2
和 7.3
版本中,所有存储桶操作都使用了现已弃用的路径样式访问模式。如果您的部署需要路径样式访问模式,则在升级时应将此设置设置为 true
。
-
disable_chunked_encoding
- 是否应禁用分块编码。如果为
false
,则启用分块编码,并在适当情况下使用。如果为true
,则禁用分块编码且不会使用,这可能意味着快照操作会消耗更多资源并需要更长时间才能完成。仅当您使用的存储服务不支持分块编码时,才应将其设置为true
。有关详细信息,请参阅 AWS Java SDK 文档。默认为false
。 -
region
- 允许指定要使用的签名区域。对于大多数用例,手动指定此设置应该不是必需的。通常,SDK 会正确猜测要使用的签名区域。它应被视为专家级设置,以支持需要 v4 签名且使用默认
us-east-1
以外的区域的与 S3 兼容的 API。默认为空字符串,这意味着 SDK 将尝试自动确定正确的签名区域。 -
signer_override
- 允许指定 S3 客户端用于签署请求的签名算法的名称。对于大多数用例,指定此设置应该不是必需的。它应被视为专家级设置,以支持不支持 SDK 自动为它们确定的签名算法的与 S3 兼容的 API。有关详细信息,请参阅 AWS Java SDK 文档。默认为空字符串,这意味着将不使用签名算法覆盖。
存储库设置
编辑s3
存储库类型支持许多设置来自定义数据在 S3 中的存储方式。这些设置可以在创建存储库时指定。例如
resp = client.snapshot.create_repository( name="my_s3_repository", repository={ "type": "s3", "settings": { "bucket": "my-bucket", "another_setting": "setting-value" } }, ) print(resp)
const response = await client.snapshot.createRepository({ name: "my_s3_repository", repository: { type: "s3", settings: { bucket: "my-bucket", another_setting: "setting-value", }, }, }); console.log(response);
PUT _snapshot/my_s3_repository { "type": "s3", "settings": { "bucket": "my-bucket", "another_setting": "setting-value" } }
支持以下设置
-
bucket
-
(必需) 用于快照的 S3 存储桶的名称。
存储桶名称必须符合 Amazon 的 S3 存储桶命名规则。
-
client
- 用于连接到 S3 的S3 客户端的名称。默认为
default
。 -
base_path
-
指定存储桶中存储库数据的路径。默认为空字符串,表示存储库位于存储桶的根目录。此设置的值不应以
/
开头或结尾。在为 Elastic Cloud Enterprise 配置快照存储库时,请勿设置
base_path
。Elastic Cloud Enterprise 会为每个部署自动生成base_path
,以便多个部署可以共享同一个存储桶。 -
chunk_size
- (字节值) Elasticsearch 在创建快照时写入存储库的对象的最大大小。大于
chunk_size
的文件将被分块为多个较小的对象。Elasticsearch 也可能会为了满足其他约束(如max_multipart_parts
限制)而将文件拆分到多个对象中。默认为5TB
,这是 AWS S3 中对象的最大大小。 -
compress
- 设置为
true
时,元数据文件将以压缩格式存储。此设置不影响默认情况下已压缩的索引文件。默认为true
。 -
max_restore_bytes_per_sec
- (可选,字节值)每个节点的最大快照恢复速率。默认为无限制。请注意,恢复也会通过恢复设置进行限制。
-
max_snapshot_bytes_per_sec
- (可选,字节值)每个节点的最大快照创建速率。默认为每秒
40mb
。请注意,如果设置了托管服务的恢复设置,则默认为无限制,并且速率还会通过恢复设置进行限制。
-
readonly
-
(可选,布尔值)如果为
true
,则存储库为只读。集群可以从存储库检索和还原快照,但不能写入存储库或在其中创建快照。只有具有写入权限的集群才能在存储库中创建快照。连接到存储库的所有其他集群应将
readonly
参数设置为true
。如果为
false
,则集群可以写入存储库并在其中创建快照。默认为false
。如果您使用多个集群注册同一个快照存储库,则只能有一个集群具有对该存储库的写入权限。多个集群同时写入存储库可能会导致存储库内容损坏。
-
server_side_encryption
- 设置为
true
时,文件将使用 AES256 算法在服务器端进行加密。默认为false
。 -
buffer_size
- (字节值)低于该阈值时,将使用单个请求上传块的最小阈值。超出此阈值后,S3 存储库将使用 AWS 多部分上传 API 将块拆分为多个部分,每个部分的长度为
buffer_size
,并在其自己的请求中上传每个部分。请注意,不允许设置小于5mb
的缓冲区大小,因为它会阻止使用多部分 API,并可能导致上传错误。也不可能设置大于5gb
的缓冲区大小,因为它是 S3 允许的最大上传大小。默认为100mb
或 JVM 堆的5%
,以较小者为准。 -
max_multipart_parts
- (整数)Elasticsearch 在单个对象的多部分上传期间将写入的最大部分数。大于
buffer_size × max_multipart_parts
的文件将被分块为多个较小的对象。Elasticsearch 也可能会为了满足其他约束(如chunk_size
限制)而将文件拆分到多个对象中。默认为10000
,这是 AWS S3 中多部分上传的最大部分数。 -
canned_acl
- S3 存储库支持所有 S3 预置 ACL:
private
、public-read
、public-read-write
、authenticated-read
、log-delivery-write
、bucket-owner-read
、bucket-owner-full-control
。默认为private
。您可以使用canned_acl
设置指定预置 ACL。当 S3 存储库创建存储桶和对象时,它会将预置 ACL 添加到存储桶和对象中。 -
storage_class
- 设置写入存储库的对象的 S3 存储类。值可以是
standard
、reduced_redundancy
、standard_ia
、onezone_ia
和intelligent_tiering
。默认为standard
。有关详细信息,请参阅 S3 存储类。 -
delete_objects_max_size
- (整数)设置用于
DeleteObjects
请求的最大批处理大小,介于 1 和 1000 之间。默认为 1000,这是 AWS DeleteObjects API 支持的最大数量。 -
max_multipart_upload_cleanup_size
- (整数)设置在每次快照删除批处理中要清理的可能悬挂的多部分上传的最大数量。默认为
1000
,这是 AWS ListMultipartUploads API 支持的最大数量。如果设置为0
,则 Elasticsearch 将不会尝试清理悬挂的多部分上传。
在存储库设置中定义客户端设置的选项(如下所述)被认为是已弃用的,将在未来的版本中删除。
除了上述设置外,您还可以在存储库设置中指定所有非安全客户端设置。在这种情况下,存储库设置中找到的客户端设置将与存储库使用的命名客户端的设置合并。客户端设置和存储库设置之间的冲突将通过存储库设置优先于客户端设置来解决。
例如
resp = client.snapshot.create_repository( name="my_s3_repository", repository={ "type": "s3", "settings": { "client": "my-client", "bucket": "my-bucket", "endpoint": "my.s3.endpoint" } }, ) print(resp)
const response = await client.snapshot.createRepository({ name: "my_s3_repository", repository: { type: "s3", settings: { client: "my-client", bucket: "my-bucket", endpoint: "my.s3.endpoint", }, }, }); console.log(response);
PUT _snapshot/my_s3_repository { "type": "s3", "settings": { "client": "my-client", "bucket": "my-bucket", "endpoint": "my.s3.endpoint" } }
这将设置一个存储库,该存储库使用客户端 my_client_name
的所有客户端设置,但 endpoint
除外,该 endpoint
被存储库设置覆盖为 my.s3.endpoint
。`
S3 存储类
编辑Amazon S3 支持多种存储类,每种存储类都提供不同的操作特性。例如,某些类的每月每字节存储成本较低,但每次请求的成本较高,而其他类在可用性保证方面可能会有所不同。
您可以使用 storage_class
存储库设置来指定 Elasticsearch 用于存储数据对象的存储类。
更改现有存储库上的 storage_class
设置只会影响新创建的对象的存储类,从而导致混合使用存储类。
您可以使用 S3 生命周期策略来调整存储库中现有对象的存储类,但您不得将对象转换为不受支持的类(如 Glacier 类),并且不得使对象过期。如果您使用 Glacier 存储类或其他不受支持的存储类或对象过期,则可能会永久失去对存储库内容的访问权限。
您可以使用 intellligent_tiering
存储类自动管理对象的类,但您不得启用可选的 Archive Access 或 Deep Archive Access 层。如果您使用这些层,则可能会永久失去对存储库内容的访问权限。
有关 S3 存储类的更多信息,请参阅 AWS 存储类指南。
推荐的 S3 权限
编辑为了将 Elasticsearch 快照进程限制为所需的最小资源,我们建议将 Amazon IAM 与预先存在的 S3 存储桶结合使用。以下是一个示例策略,该策略将允许快照访问名为“snaps.example.com”的 S3 存储桶。可以通过 AWS IAM 控制台配置此策略,方法是创建自定义策略,并使用类似于此策略的策略文档(将 snaps.example.com 更改为您的存储桶名称)。
{ "Statement": [ { "Action": [ "s3:ListBucket", "s3:GetBucketLocation", "s3:ListBucketMultipartUploads", "s3:ListBucketVersions" ], "Effect": "Allow", "Resource": [ "arn:aws:s3:::snaps.example.com" ] }, { "Action": [ "s3:GetObject", "s3:PutObject", "s3:DeleteObject", "s3:AbortMultipartUpload", "s3:ListMultipartUploadParts" ], "Effect": "Allow", "Resource": [ "arn:aws:s3:::snaps.example.com/*" ] } ], "Version": "2012-10-17" }
您可以通过在存储桶中指定前缀来进一步限制权限,在本例中,前缀名为“foo”。
{ "Statement": [ { "Action": [ "s3:ListBucket", "s3:GetBucketLocation", "s3:ListBucketMultipartUploads", "s3:ListBucketVersions" ], "Condition": { "StringLike": { "s3:prefix": [ "foo/*" ] } }, "Effect": "Allow", "Resource": [ "arn:aws:s3:::snaps.example.com" ] }, { "Action": [ "s3:GetObject", "s3:PutObject", "s3:DeleteObject", "s3:AbortMultipartUpload", "s3:ListMultipartUploadParts" ], "Effect": "Allow", "Resource": [ "arn:aws:s3:::snaps.example.com/foo/*" ] } ], "Version": "2012-10-17" }
需要存在该存储桶才能注册快照存储库。如果您没有创建存储桶,则存储库注册将失败。
使用 Kubernetes 服务帐户的 IAM 角色进行身份验证
编辑如果您想使用 Kubernetes 服务帐户进行身份验证,则需要在 S3 存储库配置目录中添加指向 $AWS_WEB_IDENTITY_TOKEN_FILE
环境变量(应由 Kubernetes pod 自动设置)的符号链接,以便存储库可以具有服务帐户的读取权限(存储库无法读取其配置目录之外的任何文件)。例如
mkdir -p "${ES_PATH_CONF}/repository-s3" ln -s $AWS_WEB_IDENTITY_TOKEN_FILE "${ES_PATH_CONF}/repository-s3/aws-web-identity-token-file"
必须在所有数据节点和主节点上创建符号链接,并且必须可由 elasticsearch
用户读取。默认情况下,Elasticsearch 使用 uid:gid 1000:0
作为用户 elasticsearch
运行。
如果存在符号链接,则默认情况下,所有没有显式 client
凭据的 S3 存储库都会使用它。
AWS VPC 带宽设置
编辑AWS 实例将 S3 端点解析为公共 IP。如果 Elasticsearch 实例位于 AWS VPC 中的私有子网中,则所有到 S3 的流量都将通过 VPC 的 NAT 实例。如果您的 VPC 的 NAT 实例是一个较小的实例大小(例如 t2.micro)或正在处理大量的网络流量,则您到 S3 的带宽可能会受到该 NAT 实例的网络带宽限制的限制。相反,我们建议创建一个 VPC 端点,该端点允许连接到位于 AWS VPC 中私有子网中的实例中的 S3。这将消除 VPC 的 NAT 实例的网络带宽带来的任何限制。
位于 AWS VPC 公有子网中的实例将通过 VPC 的互联网网关连接到 S3,并且不会受到 VPC 的 NAT 实例的带宽限制。
S3 兼容服务
编辑有许多存储系统提供 S3 兼容的 API,s3
存储库类型允许您使用这些系统来代替 AWS S3。为此,您应该将 s3.client.CLIENT_NAME.endpoint
设置为系统的端点。此设置接受 IP 地址和主机名,并且可能包含端口。例如,端点可能是 172.17.0.2
或 172.17.0.2:9000
。
默认情况下,Elasticsearch 使用 HTTPS 与您的存储系统通信,并使用 JVM 范围的信任库验证存储库的证书链。请确保 JVM 范围的信任库包含您的存储库的条目。如果您希望使用不安全的 HTTP 通信而不是 HTTPS,请将 s3.client.CLIENT_NAME.protocol
设置为 http
。
MinIO 是一个提供 S3 兼容 API 的存储系统示例。s3
存储库类型允许 Elasticsearch 使用 MinIO 支持的存储库以及存储在 AWS S3 上的存储库。其他 S3 兼容的存储系统也可能与 Elasticsearch 一起使用,但这些系统不在 Elasticsearch 测试套件的覆盖范围内。
有许多系统,包括一些来自非常知名的存储供应商的系统,声称提供 S3 兼容的 API,但实际上并没有完全模拟 S3 的行为。如果您正在使用这样的系统进行快照,请考虑使用基于标准化协议(如 NFS)的共享文件系统存储库来访问您的存储系统。s3
存储库类型需要与 S3 完全兼容。特别是,它必须支持相同的 API 端点集,具有相同的参数,在发生故障时返回相同的错误,并提供至少与 S3 一样好的(即使在多个节点并发访问时也如此)一致性和性能。您需要与您的存储系统供应商合作以解决您遇到的任何不兼容问题。请不要报告涉及声称与 S3 兼容的存储系统的 Elasticsearch 问题,除非您可以证明在使用真正的 AWS S3 存储库时也存在相同的问题。
您可以使用存储库分析 API 来执行一些对您的存储系统适用性的基本检查。如果此 API 未成功完成,或指示性能不佳,则表示您的存储系统与 AWS S3 不完全兼容,因此不适合用作快照存储库。但是,这些检查并不能保证完全兼容。
大多数存储系统都可以配置为记录它们与 Elasticsearch 交互的详细信息。如果您正在调查与 AWS S3 的可疑不兼容问题,通常最简单的方法是收集这些日志并将其提供给您的存储系统供应商以进行进一步分析。如果从存储系统发出的日志中不清楚不兼容问题,请通过将 com.amazonaws.request
日志记录器的日志记录级别设置为 DEBUG
,来配置 Elasticsearch 以记录它向 S3 API 发出的每个请求。
为了防止在日志中泄漏敏感信息(如凭据和密钥),Elasticsearch 拒绝在高详细程度下配置此记录器,除非启用了不安全的网络跟踪日志。为此,您必须通过将系统属性 es.insecure_network_trace_enabled
设置为 true
,在每个节点上显式启用它。
启用后,您可以配置 com.amazonaws.request
记录器
resp = client.cluster.put_settings( persistent={ "logger.com.amazonaws.request": "DEBUG" }, ) print(resp)
response = client.cluster.put_settings( body: { persistent: { 'logger.com.amazonaws.request' => 'DEBUG' } } ) puts response
const response = await client.cluster.putSettings({ persistent: { "logger.com.amazonaws.request": "DEBUG", }, }); console.log(response);
PUT /_cluster/settings { "persistent": { "logger.com.amazonaws.request": "DEBUG" } }
从集群中的所有节点收集涵盖失败分析时间段的 Elasticsearch 日志,并将其与分析响应一起与您的存储系统供应商共享,以便他们可以使用这些信息来确定问题所在。有关更多信息,包括有关可用于获取更详细日志的其他记录器的详细信息,请参阅AWS Java SDK 文档。在收集完供应商所需的日志后,将记录器设置恢复为 null
以返回默认日志记录配置并再次禁用不安全的网络跟踪日志。有关更多信息,请参阅 记录器 和 集群更新设置。
线性化寄存器实现
编辑S3 存储库的线性化寄存器实现基于多部分上传 API 的强一致性语义。Elasticsearch 首先创建一个多部分上传,以表明其执行线性化寄存器操作的意图。然后,Elasticsearch 列出并取消同一寄存器的所有其他多部分上传。然后,Elasticsearch 尝试完成上传。如果上传成功完成,则比较和交换操作是原子的。