ES 更新或新增
UpdateRequest updateRequest = new UpdateRequest(EsOperateTables.ORDER_TRACE_DETAIL.getAlias(), BizConstant.ES_DEFAULT_TYPE, orderTraceDetail.getId().toString()); updateRequest.doc(jsonStr, XContentType.JSON); updateRequest.docAsUpsert(true); restHighLevelClient.update(updateRequest, RequestOptions.DEFAULT);
只做更新吗,不存在会新增吗
您的问题涉及到 Elasticsearch 的更新操作逻辑。在您提供的代码中,updateRequest.docAsUpsert(true)
这个设置非常关键,它决定了当文档不存在时的行为。
关于 UpdateRequest 的行为
1. 默认行为(无 docAsUpsert 或设为 false)
java
UpdateRequest updateRequest = new UpdateRequest(index, type, id);updateRequest.doc(jsonStr, XContentType.JSON);// updateRequest.docAsUpsert(false); // 默认就是false
-
只做更新:如果文档不存在,会抛出
DocumentMissingException
-
不会新增:不会自动创建新文档
2. 使用 docAsUpsert(true) 的行为
java
UpdateRequest updateRequest = new UpdateRequest(index, type, id);updateRequest.doc(jsonStr, XContentType.JSON);updateRequest.docAsUpsert(true); // 关键设置
-
智能判断:
-
如果文档存在:执行更新操作
-
如果文档不存在:执行插入操作(相当于 upsert)
-
-
既会更新也会新增:这是一个\"更新或插入\"的操作
3. 您提供的代码分析
java
UpdateRequest updateRequest = new UpdateRequest( EsOperateTables.ORDER_TRACE_DETAIL.getAlias(), BizConstant.ES_DEFAULT_TYPE, orderTraceDetail.getId().toString()); updateRequest.doc(jsonStr, XContentType.JSON);updateRequest.docAsUpsert(true); // 这个设置为true是关键restHighLevelClient.update(updateRequest, RequestOptions.DEFAULT);
由于您设置了 docAsUpsert(true)
,所以这个操作是:
-
文档存在时:更新该文档
-
文档不存在时:插入新文档(使用提供的jsonStr作为内容)
实际应用建议
-
需要严格区分插入和更新时:
-
使用
index
API 进行明确插入 -
使用普通
update
(不带docAsUpsert) 进行明确更新
-
-
需要upsert功能时:
-
就像您现在这样设置
docAsUpsert(true)
-
这是Elasticsearch中非常常用的模式
-
-
性能考虑:
-
Upsert操作比单纯插入或更新开销稍大
-
在明确知道文档存在的情况下,可以不用docAsUpsert
-
完整示例代码
java
// 创建请求UpdateRequest request = new UpdateRequest(\"index\", \"type\", \"1\");// 准备文档内容Map jsonMap = new HashMap();jsonMap.put(\"field1\", \"value1\");jsonMap.put(\"field2\", \"value2\");// 设置更新内容request.doc(jsonMap); // 关键设置:启用upsertrequest.docAsUpsert(true);// 执行请求UpdateResponse response = client.update(request, RequestOptions.DEFAULT);// 检查结果if (response.getResult() == DocWriteResponse.Result.CREATED) { System.out.println(\"文档不存在,已新增\");} else if (response.getResult() == DocWriteResponse.Result.UPDATED) { System.out.println(\"文档已存在,已更新\");}
您当前的代码实现是正确的upsert模式,既会更新现有文档,也会在文档不存在时新增文档。