您当前的位置: 首页 >  ar

Dongguo丶

暂无认证

  • 2浏览

    0关注

    472博文

    0收益

  • 0浏览

    0点赞

    0打赏

    0留言

私信
关注
热门博文

16图解partial update实现原理

Dongguo丶 发布时间:2021-11-05 22:19:02 ,浏览量:2

1、什么是partial update?

PUT /index/type/id,创建文档&替换文档,都是一样的语法

一般对应到应用程序中,每次的执行流程基本是这样的:

(1)应用程序先发起一个get请求,获取到document,展示到前台界面,供用户查看和修改 (2)用户在前台界面修改数据,发送到后台 (3)后台代码,会将用户修改的数据在内存中进行执行,然后封装好修改后的全量数据 (4)发送PUT请求,到es中,进行全量替换 (5)es将老的document标记为deleted,然后重新创建一个新的document

partial update

post /index/type/id/_update 
{
   "doc": {
      "要修改的少数几个field即可,不需要全量的数据"
   }
}

看起来,好像就比较方便了,每次就传递少数几个发生修改的field即可

,直接将修改的数据filed更新到document中就完成了修改,不需要将全量的document数据发送过去

2、图解partial update实现原理以及其优点

partial update,看起来很方便的操作,实际内部的原理是什么样子的,然后它的优点是什么

全量修改

先要查询document的有哪些filed,因为修改要将全量的document数据发送过去,查询、修改操作在java应用中进行

image-20211105075106686

partial update局部修改

并不需要知道document的有哪些filed,只修改指定发生变化的filed即可,查询、修改操作是在shard中进行

image-20211105075213404

partial update在ES内部工作原理

image-20211105075723295

将原来的document标记为deleted,将修改后的数据写到一个新的document中

其实ES内部对partial update的工作原理和全量替换方式是几乎一样的

都是

1获取document

2将传过来的filed更新到document的json中

3将老的document标记为deleted

4将修改后的数据写到新的document中。

partial update相较于全量替换的优点

1所有的查询、修改和写回操作,都发生在es中的一个shard内部,避免了所有的网络数据传输的开销(减少2次网络请求),大大提高了性能

​ 全量替换需要读取到java应用中,必然会有网络数据传输。

2减少了查询和修改中的时间间隔,可以有效减少并发冲突的情况

​ 用户修改数据可能需要几分钟或者更长时间,才写回,那么es中的数据可能已经被别的用户修改了,那么就出现了并发冲突

​ partial update的查询、修改、写回都是发生在shard的内部,一瞬间就完成了,是毫秒级别的,所以大大减少并发冲突的情况

实战演练partial update

创建一个document

PUT /test_index/test_type/10
{
  "test_field1": "test1",
  "test_field2": "test2"
}

响应结果

{
  "_index": "test_index",
  "_type": "test_type",
  "_id": "10",
  "_version": 1,
  "result": "created",
  "_shards": {
    "total": 2,
    "successful": 1,
    "failed": 0
  },
  "created": true
}

partial update

POST /test_index/test_type/10/_update
{
  "doc": {
    "test_field2": "updated test2"
  }
}

响应结果

{
  "_index": "test_index",
  "_type": "test_type",
  "_id": "10",
  "_version": 2,
  "result": "updated",
  "_shards": {
    "total": 2,
    "successful": 1,
    "failed": 0
  }
}

查看

GET /test_index/test_type/10

响应结果

{
  "_index": "test_index",
  "_type": "test_type",
  "_id": "10",
  "_version": 2,
  "found": true,
  "_source": {
    "test_field1": "test1",
    "test_field2": "updated test2"
  }
}
3、partial update内置乐观锁并发控制 (1)partial update内置乐观锁并发控制

正常的情况,ES集群中的某个shard:

image-20211105215037939

另一个线程也在做partial update,加入这个线程先将数据先写回去了

image-20211105215607751

两个线程读取的document的version版本号都是1,此时线程B先修改数据成功,document中的version变为2,那么线程A再想修改数据,比较version不相等,修改数据失败,会自动partial update fail

image-20211105215839406

(2)retry_on_conflict

修改失败,可以使用retry策略,retry_on_conflict表示会重新尝试,并指定重试的次数

post /index/type/id/_update?retry_on_conflict=5
retry策略

1再次获取document的数据和罪行版本号

2基于最新版本号再次去更新,

3如果还是失败,重复1、2两个步骤,重试最大次数可以通过retry_on_conflict指定

关注
打赏
1638062488
查看更多评论
立即登录/注册

微信扫码登录

0.0362s