分片分配感知
Elastic Stack 自我管理
您可以使用自定义节点属性作为感知属性,使 Elasticsearch 在分配分片时考虑到您的物理硬件配置。如果 Elasticsearch 知道哪些节点在同一物理服务器、同一机架或同一区域中,它可以分配主分片及其副本分片,以最大限度地降低在发生故障时丢失所有分片副本的风险。
当通过 cluster.routing.allocation.awareness.attributes
设置启用分片分配感知时,分片只会分配给设置了指定感知属性值的节点。如果您使用多个感知属性,Elasticsearch 在分配分片时会分别考虑每个属性。
属性值的数量决定了每个位置分配的分片副本数量。如果每个位置的节点数量不平衡,并且有很多副本,则副本分片可能会保持未分配状态。
了解更多关于设计弹性集群的信息。
启用分片分配感知的步骤
使用自定义节点属性指定每个节点的位置。例如,如果您希望 Elasticsearch 将分片分布在不同的机架上,则可以使用名为
rack_id
的感知属性。您可以通过两种方式设置自定义属性
通过编辑
elasticsearch.yml
配置文件node.attr.rack_id: rack_one
在启动节点时使用
-E
命令行参数./bin/elasticsearch -Enode.attr.rack_id=rack_one
通过在每个符合主节点条件的节点的
elasticsearch.yml
配置文件中设置cluster.routing.allocation.awareness.attributes
,来告知 Elasticsearch 在分配分片时考虑一个或多个感知属性。cluster.routing.allocation.awareness.attributes: rack_id
- 将多个属性指定为逗号分隔的列表。
您还可以使用cluster-update-settings API 来设置或更新集群的感知属性
PUT /_cluster/settings
{ "persistent" : { "cluster.routing.allocation.awareness.attributes" : "rack_id" } }
使用此示例配置,如果您启动两个 node.attr.rack_id
设置为 rack_one
的节点,并创建一个具有 5 个主分片和每个主分片 1 个副本的索引,则所有主分片和副本都将在两个节点上分配。

如果您添加两个 node.attr.rack_id
设置为 rack_two
的节点,Elasticsearch 会将分片移动到新节点,确保(如果可能)同一分片的两个副本不在同一机架中。

如果 rack_two
发生故障并导致其两个节点都关闭,默认情况下,Elasticsearch 会将丢失的分片副本分配给 rack_one
中的节点。为了防止特定分片的多个副本分配在同一位置,您可以启用强制感知。
默认情况下,如果一个位置发生故障,Elasticsearch 会将其分片分布在剩余的位置上。如果集群没有足够的资源来承载所有分片,则当一个位置丢失时,这可能是不希望的。
为了防止剩余位置在整个位置发生故障时过载,请使用 cluster.routing.allocation.awareness.force.*
设置指定应存在的属性值。这意味着,如果只有一个位置可用,Elasticsearch 将宁愿保留一些未分配的副本,而不是使剩余位置中的节点过载。
例如,如果您有一个名为 zone
的感知属性,并且在 zone1
和 zone2
中配置了节点,则可以使用强制感知来使 Elasticsearch 在只有一个区域可用时保留一半的分片副本未分配
cluster.routing.allocation.awareness.attributes: zone
cluster.routing.allocation.awareness.force.zone.values: zone1,zone2
- 指定所有可能的
zone
属性值。
使用此示例配置,如果您有两个 node.attr.zone
设置为 zone1
的节点和一个 number_of_replicas
设置为 1
的索引,则 Elasticsearch 会分配所有主分片,但不分配任何副本。一旦 node.attr.zone
具有不同值的节点加入集群,它将分配副本分片。相反,如果您不配置强制感知,Elasticsearch 会将所有主分片和副本分配给两个节点,即使它们位于同一区域中也是如此。