Elasticsearch的路由(Routing)特性

2024-03-18 17:38

本文主要是介绍Elasticsearch的路由(Routing)特性,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

Elasticsearch路由机制介绍

Elasticsearch的路由机制与其分片机制有着直接的关系。Elasticsearch的路由机制即是通过哈希算法,将具有相同哈希值的文档放置到同一个主分片中。这个和通过哈希算法来进行负载均衡几乎是一样的。

 

而Elasticsearch也有一个默认的路由算法:它会将文档的ID值作为依据将其哈希到相应的主分片上,这种算法基本上会保持所有数据在所有分片上的一个平均分布,而不会产生数据热点。

 

而我们为什么会需要自定义的Routing模式呢?首先默认的Routing模式在很多情况下都是能满足我们的需求的——平均的数据分布、对我们来说是透明的、多数时候性能也不是问题。但是在我们更深入地理解我们的数据的特征之后,使用自定义的Routing模式可能会给我们带来更好的性能。

 

假设你有一个100个分片的索引。当一个请求在集群上执行时会发生什么呢?

1. 这个搜索的请求会被发送到一个节点

2. 接收到这个请求的节点,将这个查询广播到这个索引的每个分片上(可能是主分片,也可能是复制分片)

3. 每个分片执行这个搜索查询并返回结果

4. 结果在通道节点上合并、排序并返回给用户

 

因为默认情况下,Elasticsearch使用文档的ID(类似于关系数据库中的自增ID,当然,如果不指定ID的话,Elasticsearch使用的是随机值)将文档平均的分布于所有的分片上,这导致了Elasticsearch不能确定文档的位置,所以它必须将这个请求广播到所有的100个分片上去执行。这同时也解释了为什么主分片的数量在索引创建的时候是固定下来的,并且永远不能改变。因为如果分片的数量改变了,所有先前的路由值就会变成非法了,文档相当于丢失了。

 

而自定义的Routing模式,可以使我们的查询更具目的性。我们不必盲目地去广播查询请求,取而代之的是:我们要告诉Elasticsearch我们的数据在哪个分片上。

 

原来的查询语句:“请告诉我,USER1的文档数量一共有多少”

使用自定义Routing(在USESR ID上)后的查询语句:“请告诉我,USER1的文档数量一共有多少,它就在第三个分片上,其它的分片就不要去扫描了”

 

指定个性化路由

所有的文档API(get,index,delete,update和mget)都能接收一个routing参数,可以用来形成个性化文档分片映射。一个个性化的routing值可以确保相关的文档存储到同样的分片上——比如,所有属于同一个用户的文档。

 

第一种方法,也是比较直观的方法就是直接在请求的URL中指定routing参数:

[plain] view plain copy
print ?
  1. curl -XPOST 'http://localhost:9200/store/order?routing=user123' -d '  
  2. {  
  3.     "productName": "sample",  
  4.     "customerID": "user123"  
  5. }'  
curl -XPOST 'http://localhost:9200/store/order?routing=user123' -d '
{"productName": "sample","customerID": "user123"
}'


这样我们就按照用户的customerID的值将具有相同customerID的文档置于同一分片上了。

 

 

第二种方法就是直接从文档中提取到对应的路由值:

[plain] view plain copy
print ?
  1. curl -XPUT 'http://localhost:9200/store/order/_mapping' -d '  
  2. {  
  3.     "order": {  
  4.         "_routing": {  
  5.             "required": true,  
  6.             "path": "customerID"  
  7.         }  
  8.     }  
  9. }'  
curl -XPUT 'http://localhost:9200/store/order/_mapping' -d '
{"order": {"_routing": {"required": true,"path": "customerID"}}
}'


这样的方法和第一种方法在效果上一样的,但是有一点需要注意,相比于第一种方法这种方法的效率稍低,因为第一种方法直接就在请求的参数中确定了路由的值,而第二种方法中,首先需要将文档读入之后,再从中提取到对应的路由值。

 

 

利用路由机制的查询

利用路由机制的查询也是非常简单明了的,只需要在查询中指定对应的路由值即可:

[plain] view plain copy
print ?
  1. curl -XGET 'http://localhost:9200/store/order/_search?routing=user123' -d '  
  2. {  
  3.     "query": {  
  4.         "filtered": {  
  5.             "query": {  
  6.                 "match_all": {}  
  7.             },  
  8.             "filter": {  
  9.                 "term": {  
  10.                     "userID": "user123"  
  11.                 }  
  12.             }  
  13.         }  
  14.     }  
  15. }'  
curl -XGET 'http://localhost:9200/store/order/_search?routing=user123' -d '
{"query": {"filtered": {"query": {"match_all": {}},"filter": {"term": {"userID": "user123"}}}}
}'


通过指定的路由值,我们就可以直接定位到user123的文档所在的分片,而不用一股脑的向索引的所有节点都发送请求。这样的话,会大大减少系统资源的浪费。

 

 

当然,也可以同时指定多个路由值,方法也是显而易见的,只需要在查询参数中指定多个路由值即可:

[plain] view plain copy
print ?
  1. curl -XGET 'http://localhost:9200/forum/posts/?routing=Admin,Moderator' -d '{}'  
curl -XGET 'http://localhost:9200/forum/posts/?routing=Admin,Moderator' -d '{}'



 

路由机制的总结

实际上,如果不明确指明使用路由机制,实际上路由机制也是在发挥作用的,只是默认的路由值是文档的id而已。而个性化路由的需求主要是和业务相关的。默认的路由(如果是自动的生成的id)直观上会把所有的文档随机分配到一个分片上,而个性化的路由值就是和业务相关的了。这也会造成一些潜在的问题,比如user123本身的文档就非常多,有数十万个,而其他大多数的用户只有几个文档,这样的话就会导致user123所在的分片较大,出现数据偏移的情况,特别是多个这样的用户处于同一分片的时候,现象会更明显。具体的使用还是要结合实际的应用场景来选择的。

这篇关于Elasticsearch的路由(Routing)特性的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/823122

相关文章

Elasticsearch 在 Java 中的使用教程

《Elasticsearch在Java中的使用教程》Elasticsearch是一个分布式搜索和分析引擎,基于ApacheLucene构建,能够实现实时数据的存储、搜索、和分析,它广泛应用于全文... 目录1. Elasticsearch 简介2. 环境准备2.1 安装 Elasticsearch2.2 J

SpringIntegration消息路由之Router的条件路由与过滤功能

《SpringIntegration消息路由之Router的条件路由与过滤功能》本文详细介绍了Router的基础概念、条件路由实现、基于消息头的路由、动态路由与路由表、消息过滤与选择性路由以及错误处理... 目录引言一、Router基础概念二、条件路由实现三、基于消息头的路由四、动态路由与路由表五、消息过滤

新特性抢先看! Ubuntu 25.04 Beta 发布:Linux 6.14 内核

《新特性抢先看!Ubuntu25.04Beta发布:Linux6.14内核》Canonical公司近日发布了Ubuntu25.04Beta版,这一版本被赋予了一个活泼的代号——“Plu... Canonical 昨日(3 月 27 日)放出了 Beta 版 Ubuntu 25.04 系统镜像,代号“Pluc

Rust中的Drop特性之解读自动化资源清理的魔法

《Rust中的Drop特性之解读自动化资源清理的魔法》Rust通过Drop特性实现了自动清理机制,确保资源在对象超出作用域时自动释放,避免了手动管理资源时可能出现的内存泄漏或双重释放问题,智能指针如B... 目录自动清理机制:Rust 的析构函数提前释放资源:std::mem::drop android的妙

ElasticSearch+Kibana通过Docker部署到Linux服务器中操作方法

《ElasticSearch+Kibana通过Docker部署到Linux服务器中操作方法》本文介绍了Elasticsearch的基本概念,包括文档和字段、索引和映射,还详细描述了如何通过Docker... 目录1、ElasticSearch概念2、ElasticSearch、Kibana和IK分词器部署

Go路由注册方法详解

《Go路由注册方法详解》Go语言中,http.NewServeMux()和http.HandleFunc()是两种不同的路由注册方式,前者创建独立的ServeMux实例,适合模块化和分层路由,灵活性高... 目录Go路由注册方法1. 路由注册的方式2. 路由器的独立性3. 灵活性4. 启动服务器的方式5.

关于Gateway路由匹配规则解读

《关于Gateway路由匹配规则解读》本文详细介绍了SpringCloudGateway的路由匹配规则,包括基本概念、常用属性、实际应用以及注意事项,路由匹配规则决定了请求如何被转发到目标服务,是Ga... 目录Gateway路由匹配规则一、基本概念二、常用属性三、实际应用四、注意事项总结Gateway路由

Java实现Elasticsearch查询当前索引全部数据的完整代码

《Java实现Elasticsearch查询当前索引全部数据的完整代码》:本文主要介绍如何在Java中实现查询Elasticsearch索引中指定条件下的全部数据,通过设置滚动查询参数(scrol... 目录需求背景通常情况Java 实现查询 Elasticsearch 全部数据写在最后需求背景通常情况下

Java操作ElasticSearch的实例详解

《Java操作ElasticSearch的实例详解》Elasticsearch是一个分布式的搜索和分析引擎,广泛用于全文搜索、日志分析等场景,本文将介绍如何在Java应用中使用Elastics... 目录简介环境准备1. 安装 Elasticsearch2. 添加依赖连接 Elasticsearch1. 创

五大特性引领创新! 深度操作系统 deepin 25 Preview预览版发布

《五大特性引领创新!深度操作系统deepin25Preview预览版发布》今日,深度操作系统正式推出deepin25Preview版本,该版本集成了五大核心特性:磐石系统、全新DDE、Tr... 深度操作系统今日发布了 deepin 25 Preview,新版本囊括五大特性:磐石系统、全新 DDE、Tree