更新符合特定条件的ElasticSearch文档

时间:2017-10-10 16:41:39

标签: elasticsearch elasticsearch-5

我想批量更新符合条件的文件 ES版本:5.1.1
指数:index_1234
输入:地址
网址:发布http://localhost:9200/index_1234/addresses/_update_by_query
有效负载:

{
    "id":1,
    "address":"temp address"
}

我使用以下内联脚本来更新文档

{
  "script": {
     "inline": "if(ctx._source.containsKey(\"address\") && ctx._source.address == "temp address"){ctx._source.address='perm address'}"
  }
}

即如果“地址”字段的值为“临时地址”,我将其替换为“烫发地址”

此脚本完美运行并仅更新匹配的文档。 不过我有疑问

假设共有10个文件,其中5个“地址”字段为“临时地址”,5个“地址”字段为“烫发地址”

在执行上述脚本时,它提供以下o / p

{
    "took": 131,
    "timed_out": false,
    "total": 10,
    **"updated": 10**,
    "deleted": 0,
    "batches": 1,
    "version_conflicts": 0,
    "noops": 0,
    "retries": {
        "bulk": 0,
        "search": 0
    },
    "throttled_millis": 0,
    "requests_per_second": -1,
    "throttled_until_millis": 0,
    "failures": []
}

所以虽然它只更新了5个文件(我已经仔细检查过),但在最终回复中它说“更新”:10。我期待“更新”:5,我错过了什么? 它更新其他什么?我可以看到“_version”更新了所有文档,即使是没有匹配字符串的文档 提前致谢 !

更新

非常感谢Mike快速回复:)
根据Mike字段检查,更新查询应更新如下。

"query": {
  "exists": {
    "field": "address"
  }
}

然而还有一个问题 最初,为了简化问题,我将字段保持在最小。 实际上有效载荷中有很多字段,我想根据某些条件更新其中的3个字段。

因此,有效载荷如下

{
    "id":12,
    "address":"temp address",
    "email":"temp email",
    "phone":"temp phone",
    .
    .
    .
}

我正在使用以下脚本来更新所有3个字段

{
  "script": {
     "inline": "if(ctx._source.containsKey(\"address\") && ctx._source.address == "temp address"){ctx._source.address='perm address'}if(ctx._source.containsKey(\"email\") && ctx._source.email == "temp email"){ctx._source.email='perm email'}if(ctx._source.containsKey(\"phone\") && ctx._source.phone == "temp phone"){ctx._source.phone='perm phone'}"
  }
}

我们可以更新Mike的多个领域的解决方案吗?或者我们可以采取其他替代方式吗? 再次感谢 !

1 个答案:

答案 0 :(得分:2)

这种情况正在发生,因为即使您实际上没有修改在_update_by_query请求中检索的所有文档,它们也至少被视为查询中的命中。

不是在更新查询中进行现场检查,而是将此现有查询添加到更新请求中:

"query": {
  "exists": {
    "field": "address"
  }
}

编辑以回复更新的问题: 如果您想更新3个字段,那么您最有可能通过单个脚本进行3个同时修改的最简单时间。如上所示,计数并不真正反映对文档进行的实际修改。如果绝对需要计数,你可以这样做(并且它会过滤到任何具有这3个中任何一个的文档。)

"query": {
  "bool": {
    "minimum_should_match": 1,
    "should": [
      {
        "term": {
          "address": {
            "value": "temp address"
          }
        }
      },
      {
        "term": {
          "email": {
            "value": "temp email"
          }
        }
      },
      {
      "term": {
        "phone": {
          "value": "temp phone"
        }
      }
    }
  ]
  }
  }