【问题标题】:Elasticsearch 7.13 - elastic search response with old data after update apiElasticsearch 7.13 - 更新 api 后旧数据的弹性搜索响应
【发布时间】:2021-07-27 20:47:00
【问题描述】:

我们使用弹性 7.13 我们正在使用 upsert 定期更新索引

操作顺序

  1. 使用动态映射创建新索引all strings mapped as text

     "dynamic_templates": [
     {
       "strings_as_keywords": {
         "match_mapping_type": "string",
         "mapping": {
           "type": "text",
           "analyzer": "autocomplete",
           "search_analyzer": "search_term_analyzer",
           "copy_to": "_all",
           "fields": {
             "keyword": {
               "type": "keyword",
               "normalizer": "lowercase_normalizer"
             }
           }
         }
       }
     }
    

    ]

  2. 使用附加代码批量插入(我没有与其余代码等效的)

  3. 搜索特定字段

    localhost:9200/mdsearch-vitaly123/_search
     {
       "query": {
         "match": {
           "fullyQualifiedName": `value_test`
         }
       }
     }
    
  4. 得到 1 个结果

  5. 现在再次插入 "fullyQualifiedName": "value_test1234"(如第 2 步)

  6. 按照步骤 3 进行搜索

  7. 得到 2 个结果 1 个带有“fullyQualifiedName”的文档:“value_test” 和其他“fullyQualifiedName”:“value_test1234”

sn-p 下面的 upsert(第 2 步):

@Override
    public List<BulkItemStatus> updateDocumentBulk(String indexName, List<JsonObject> indexDocuments) throws MDSearchIndexerException {
        BulkRequest request = new BulkRequest().setRefreshPolicy(WriteRequest.RefreshPolicy.IMMEDIATE);
        ofNullable(indexDocuments).orElseThrow(NullPointerException::new)
                .forEach(x -> {
                var id = x.get("_id").getAsString();
                x.remove("_id");
                    request.add(new UpdateRequest(indexName, id)
                            .docAsUpsert(true)
                            .doc(x.toString(), XContentType.JSON)
                            .retryOnConflict(3)
                    );
                });
        BulkResponse bulk = elasticsearchRestClient.bulk(request, RequestOptions.DEFAULT);
        return stream(bulk.getItems())
                .map(r -> new BulkItemStatus(r.getId(), isSuccess(r), r.getFailureMessage()))
                .collect(Collectors.toList());
    }

我可以按更新的属性进行搜索。

但问题是搜索会检索“更新的字段”和以前的字段。

我该如何解决? 可能会以某种方式将版本号限制为只有 1。

我设置了setRefreshPolicy(WriteRequest.RefreshPolicy.IMMEDIATE),但没有帮助

在图片中我们可以看到结果

P.S - 也检索到旧数据和更新数据

建议?

问候,

【问题讨论】:

  • 当您更新一个文档时,版本总是会增加,当您检索文档时您检索的是实际文档的内容,之前的文档将永远消失。所以我不确定你所说的“旧数据”是什么意思。 ES 不保留给定文档的多个版本,只保留最后一个版本。也许向我们展示一个序列(获取、更新、获取)以及您认为不正确的地方?
  • @Val - 我已经更新了我的问题
  • 你能打开你得到的两个点击吗?它们必须有不同的 ID,这意味着您没有进行任何更新,而只是使用新 ID 插入

标签: java elasticsearch


【解决方案1】:

发生的情况是以下行必须产生null

var id = x.get("_id").getAsString();

换句话说,您在indexDocuments 中传递的JSON 文档中没有_id 字段。源文档中不允许有带有下划线字符的字段。如果是这种情况,您会收到以下错误:

字段 [_id] 是元数据字段,不能添加到文档中。使用索引 API 请求参数。

因此,您的更新请求无法更新任何文档(因为没有标识要更新的文档的 ID)并且只会插入一个新文档(即 docAsUpsert 所做的),这就是您看到两个不同文档的原因.

【讨论】:

  • 是的,我有不同的文档 ID 作为响应。如您所说,我正在尝试查看我是否有空 ID。基本上我是从 DB 拿走它们,我认为不可能
  • 我认为您获取 ID 的方式不正确。尝试转储 JSON 文档,您会看到。请展示您获得的两个点击量,我们将看看它的外观。
  • 认为你是对的,我从外面得到了不同的 id 并且 ES 将其插入为新的
  • 这是唯一的解释,如果您设法为 ID 找到正确的字段,那么您的代码将按预期工作。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-11-12
  • 1970-01-01
  • 2016-08-27
  • 1970-01-01
  • 2020-03-31
  • 2015-05-23
  • 1970-01-01
相关资源
最近更新 更多