当索引一个文档的时候,文档会被存储到一个主分片中。 Elasticsearch 如何知道一个文档应该存放到哪个分片中呢?当我们创建文档时,它如何决定这个文档应当被存储在分片 1 还是分片 2 中呢?
首先这肯定不会是随机的,否则将来要获取文档的时候我们就不知道从何处寻找了。实际上,这个过程是根据下面这个公式决定的:
shard_num = hash(routing) % number_of_primary_shards
routing 是一个可变值,默认是文档的 _id ,也可以设置成一个自定义的值。 routing 通过 hash 函数生成一个数字,然后这个数字再除以 number_of_primary_shards (主分片的数量)后得到 余数 。这个分布在 0 到 number_of_primary_shards-1 之间的余数,就是我们所寻求的文档所在分片的位置。
这就解释了为什么我们要在创建索引的时候就确定好主分片的数量 并且永远不会改变这个数量:因为如果数量变化了,那么所有之前路由的值都会无效,文档也再也找不到了。

自定义routing: 表示文档根据'kimchy'进行路由

POST twitter/mytype?routing=kimchy
{
"user" : "kimchy",
"post_date" : "2009-11-15T14:12:12",
"message" : "trying out Elasticsearch"
}

根据routing值查询
GET twitter/mytype/1?routing=kimchy

或者

GET my_index/mytype/_search
{
"query": {
"terms": {
"_routing": [ "kimchy" ]
}
}
}

将请求发送到主动的routing上

GET my_index/_search?routing=user1,user2
{
"query": {
"match": {
"title": "document"
}
}
}

指定CRUD操作必须指定routing值

put 10.127.0.1:9200/myrouting/_mapping
{
"myrouting": {
"mappings": {
"my_type": {
"_routing": { "required": true },
"properties": {
"name": { "type": "keyword" }
}
}
}
}
}

请求时不指定routing值错误演示

post 10.127.0.1:9200/myrouting/my_type/1
{
"error": {
"root_cause": [
{
"type": "routing_missing_exception",
"reason": "routing is required for [myrouting]/[my_type]/[1]",
"index_uuid": "_na_",
"index": "myrouting"
}
],
"type": "routing_missing_exception",
"reason": "routing is required for [myrouting]/[my_type]/[1]",
"index_uuid": "_na_",
"index": "myrouting"
},
"status": 400
}

所有的文档 API( get 、 index 、 delete 、 bulk 、 update 以及 mget )都接受一个叫做 routing 的路由参数 ,通过这个参数我们可以自定义文档到分片的映射。一个自定义的路由参数可以用来确保所有相关的文档——例如所有属于同一个用户的文档——都被存储到同一个分片中。
而我们为什么会需要自定义的Routing模式呢?首先默认的Routing模式在很多情况下都是能满足我们的需求的——平均的数据分布、对我们来说是透明的、多数时候性能也不是问题。但是在我们更深入地理解我们的数据的特征之后,使用自定义的Routing模式可能会给我们带来更好的性能。

自定义路由可能会导致索引分配不均,大量的索引路由到一个分片上,导致这个分片的索引和查询性能降低。为了解决这个问题,可以设置 routing_partition_size 参数。(注意这是一个索引级别的设置,只能在创建索引的时候设置。随着分区大小的增加,数据分布越均匀,代价是每个请求必须搜索更多分片)这样routing将路由到一组分片,然后_id字段在决定文档保存到那一个分片上。由于这个原因。routing_partition_size的值必须是一个大于1但是小于number_of_shards设置的分片数量的一个整数。具体公式如下:
shard_num = (hash(_routing) + hash(_id) % routing_partition_size) % num_primary_shards

请求发到某个节点之后,该节点成为协调节点,计算好routing值之后转发到指定的节点(增删改需求发送到primary shard,查询需求主分片和副本分片都可以,对于查询需求发送到主分片还是副本分片是通过轮询查询中所有的分片),然后将数据返回到协调节点,协调节点将数据返回给客户端

最新文章

  1. js封装的三级联动菜单(使用时只需要一行js代码)
  2. Android 启动后页面跳转
  3. EBS中加载FORM使用的JavaBean的JAR包
  4. Supervisor – 用于 Unix 系统的进程监控工具
  5. Noip2014 提高组 day1 T1· 生活大爆炸版石头剪刀布
  6. 关于Eclispe插件开发起步(一)
  7. PHP mongoDB 操作
  8. 使用nice命令调整进程优先级
  9. BNUOJ flower (搜索)
  10. ie8下下拉菜单文字为空
  11. file 多次上传附件功能完善
  12. HTTP高并发调优小记
  13. drf视图组件、认证组件
  14. Java Mongo 自定义序列化笔记
  15. python学习 day21 (3月28日)----(抽象类 多态 nametuple dump)
  16. js如何给当前日期+1?
  17. ES6——内置对象的扩展
  18. VB.NET & Visual Basic
  19. 【LG5020】[NOIP2018]货币系统
  20. 最小生成树-Borůvka算法

热门文章

  1. leetcode-45.跳跃游戏II(hard)
  2. 卷积神经网络快速入门【基于TensorFlow】
  3. centos 7 安装webmin
  4. angularcli 第二篇(数据绑定、属性申明、绑定属性)
  5. 【转】高性能网络编程3----TCP消息的接收
  6. keekalived+nginx 高可用
  7. Jenkins 插件:Job Configuration History(记录job的历史更新记录)
  8. HTML&CSS基础-子元素的伪类选择器
  9. Problem G: STL——整理唱片(list的使用)
  10. 《The One !团队》:BETA Scrum metting2