2021-12-15

背景

源于一个不认真看elasticsearch的误会,有新需求需要用到es的BULK API中的update方法。使用这个方法,加入更新的文档没有变更(即更新前后是一样的)默认不会更新,result返回noop,version等均不会被更新(可以理解为mysql的upsert)。

先创建一条数据:

POST  _bulk  {  "index"  :  {  "_index"  :  "test",  "_id"  :  "1"  }  }  {  "field1"  :  "value1"  }

误会来自于以下操作:

POST  _bulk  {  "update"  :  {"_id"  :  "1",  "_index"  :  "test"}  }  {  "doc"  :  {"field2"  :  "value2"}  }
POST  _bulk  {  "index"  :  {"_id"  :  "1",  "_index"  :  "test"}  }  {  "doc"  :  {"field2"  :  "value2"}  } 
POST  _bulk {  "update"  :  {"_id"  :  "1",  "_index"  :  "test"}  } {  "doc"  :  {"field2"  :  "value2"}  } 
POST  _bulk {  "update"  :  {"_id"  :  "1",  "_index"  :  "test"}  } {  "doc"  :  {"field2"  :  "value2"}  }

连续执行以上语句,第一次是返回noop,第二次返回updated,第三次返回updata的,第四次返回noop

问题在于为什么第三次返回updated而不是noop呢?

查了好久资料没发现,看源码也没发现。只是有很多if else分支,怀疑是否某个条件不满足所有被updated,遂自己debug源码找答案。

调试环境搭建

1.下载源码,并导入eclipse。具体可直接看es git的https://github.com/elastic/elasticsearch/blob/master/CONTRIBUTING.md,里面有介绍说明。

2.在docker上跑起ES,注意需要与源码分支版本一致,本次使用7.14分支。

<pre class="brush:bash;">#拉取镜像
docker pull docker.io/elasticsearch:7.14.0

查看镜像id

docker image|grep elastic

找出IDrun起来,加上远程debug参数

docker run -d --name es7.14 -p 9200:9200 -p 9300:9300 -p 5678:5678/tcp -e "discovery.type=single-node" -e ES_JAVA_OPTS="-agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=0.0.0.0:5678" e347b2b2d6c1

3.eclpise连接远程


eclipse.jpg

debug过程

debug.jpg

被update的原因在与key是不一样的,一个是{doc={field2=value2}},一个是field2=value2

发现原来doc在index跟update含义是不一样的。在index会当成key操作,在update是关键字,里面内容才是更新的map


doc.jpg
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

友情链接更多精彩内容