Elasticsearch 无痛脚本不使用 if 条件替换嵌套对象字段值
Elasticsearch painless script not replacing the nested object field value using if condition
我刚开始使用 ES,并且仍在学习交易技巧!!!
我需要 replace/overwrite 嵌套对象类型的字段之一。
这是示例文档:
{
"name":"db_ref",
"ref_counter":[
{"ref_name":"test1","count":1},
{"ref_name":"test2","count":2},
{"ref_name":"test3","count":3}
]
}
上述文档的映射:
{
"settings": {
"mappings": {
"test_doc": {
"properties": {
"name": {
"type": "string"
},
"ref_count": {
"type": "nested",
"ref_name": "string",
"count": "long"
}
}
}
}
}
}
我需要更新给定 ref_name 的计数字段值。例如,在上面的例子中,如果 ref_name 是 "test1" 我想要新的 count 为 500。
我想出了下面的 painless 脚本 来更改 count 值,它执行得很好,没有任何错误,但我没有看到正在更新的值。
curl -XPOST "http://localhost:9200/test_type/test_type/test_db/_update" -d '
{"script": "if (ctx._source.ref_counter.ref_name == cur_ref
&& ctx._source.ref_counter.count == cur_count)
{ctx._source.ref_counter.count = new_count };",
"params": {"cur_count": 1,"new_count": 500, "cur_ref": "test1"}}}'
以下是回复:
{"_index":"test_index","_type":"test_type","_id":"test_db","_version":2}
但是当我看到文档时它仍然具有旧值。
谁能帮我把计数值改成新值。
我已经提到了以下查询。 (Bulk update
查询和 per document
更新查询)
核心逻辑在script
中,这在两个查询中是相同的。
我建议您仔细阅读逻辑,因为它不言自明。基本上,脚本遍历嵌套文档,并根据您声明的条件,相应地更新 count
。
批量更新 - 使用 _update_by_query
POST <your_index_name>/_update_by_query
{
"query": {
"match_all": {}
},
"script": {
"lang": "painless",
"source": """
if(ctx._source.ref_counter.contains(params.cur_data)){
for(int i=0; i<ctx._source.ref_counter.size(); i++)
{
HashMap myKV = ctx._source.ref_counter.get(i);
if(myKV.get(params.key_ref)==params.key_ref_value){
myKV.put(params.key_count, params.key_count_value_new);
}
}
//ctx._source.ref_counter.add(params.new_data);
}""",
"params": {
"cur_data": { "ref_name": "test2", "count": 2},
"new_data": { "ref_name": "test2", "count": 22},
"key_ref": "ref_name",
"key_ref_value": "test2",
"key_count": "count",
"key_count_value_new": 80
}}
}
每个文档更新 - 使用 文档 ID
POST <your_index_name>/<your_mapping>/1/_update
{
"script": {
"lang": "painless",
"source": """
if(ctx._source.ref_counter.contains(params.cur_data)){
for(int i=0; i<ctx._source.ref_counter.size(); i++)
{
HashMap myKV = ctx._source.ref_counter.get(i);
if(myKV.get(params.key_ref)==params.key_ref_value){
myKV.put(params.key_count, params.key_count_value_new);
}
}
//ctx._source.ref_counter.add(params.new_data);
}""",
"params": {
"cur_data": { "ref_name": "test2", "count": 2},
"new_data": { "ref_name": "test2", "count": 22},
"key_ref": "ref_name",
"key_ref_value": "test2",
"key_count": "count",
"key_count_value_new": 80
}
}
}
希望对您有所帮助,如果您有任何疑问,请告诉我!
我刚开始使用 ES,并且仍在学习交易技巧!!! 我需要 replace/overwrite 嵌套对象类型的字段之一。 这是示例文档:
{
"name":"db_ref",
"ref_counter":[
{"ref_name":"test1","count":1},
{"ref_name":"test2","count":2},
{"ref_name":"test3","count":3}
]
}
上述文档的映射:
{
"settings": {
"mappings": {
"test_doc": {
"properties": {
"name": {
"type": "string"
},
"ref_count": {
"type": "nested",
"ref_name": "string",
"count": "long"
}
}
}
}
}
}
我需要更新给定 ref_name 的计数字段值。例如,在上面的例子中,如果 ref_name 是 "test1" 我想要新的 count 为 500。 我想出了下面的 painless 脚本 来更改 count 值,它执行得很好,没有任何错误,但我没有看到正在更新的值。
curl -XPOST "http://localhost:9200/test_type/test_type/test_db/_update" -d '
{"script": "if (ctx._source.ref_counter.ref_name == cur_ref
&& ctx._source.ref_counter.count == cur_count)
{ctx._source.ref_counter.count = new_count };",
"params": {"cur_count": 1,"new_count": 500, "cur_ref": "test1"}}}'
以下是回复:
{"_index":"test_index","_type":"test_type","_id":"test_db","_version":2}
但是当我看到文档时它仍然具有旧值。
谁能帮我把计数值改成新值。
我已经提到了以下查询。 (Bulk update
查询和 per document
更新查询)
核心逻辑在script
中,这在两个查询中是相同的。
我建议您仔细阅读逻辑,因为它不言自明。基本上,脚本遍历嵌套文档,并根据您声明的条件,相应地更新 count
。
批量更新 - 使用 _update_by_query
POST <your_index_name>/_update_by_query
{
"query": {
"match_all": {}
},
"script": {
"lang": "painless",
"source": """
if(ctx._source.ref_counter.contains(params.cur_data)){
for(int i=0; i<ctx._source.ref_counter.size(); i++)
{
HashMap myKV = ctx._source.ref_counter.get(i);
if(myKV.get(params.key_ref)==params.key_ref_value){
myKV.put(params.key_count, params.key_count_value_new);
}
}
//ctx._source.ref_counter.add(params.new_data);
}""",
"params": {
"cur_data": { "ref_name": "test2", "count": 2},
"new_data": { "ref_name": "test2", "count": 22},
"key_ref": "ref_name",
"key_ref_value": "test2",
"key_count": "count",
"key_count_value_new": 80
}}
}
每个文档更新 - 使用 文档 ID
POST <your_index_name>/<your_mapping>/1/_update
{
"script": {
"lang": "painless",
"source": """
if(ctx._source.ref_counter.contains(params.cur_data)){
for(int i=0; i<ctx._source.ref_counter.size(); i++)
{
HashMap myKV = ctx._source.ref_counter.get(i);
if(myKV.get(params.key_ref)==params.key_ref_value){
myKV.put(params.key_count, params.key_count_value_new);
}
}
//ctx._source.ref_counter.add(params.new_data);
}""",
"params": {
"cur_data": { "ref_name": "test2", "count": 2},
"new_data": { "ref_name": "test2", "count": 22},
"key_ref": "ref_name",
"key_ref_value": "test2",
"key_count": "count",
"key_count_value_new": 80
}
}
}
希望对您有所帮助,如果您有任何疑问,请告诉我!