Добавить поле даты и логическое значение с помощью ? в имени к существующим документам Elasticsearch

#elasticsearch

#elasticsearch

Вопрос:

Нам нужно добавить два новых поля в существующий экземпляр ElasticSearch (7.9 oss).

Поле 1: Поле даты

Мы хотим добавить необязательное поле даты. Оно не должно иметь значения при создании. Как это сделать с update_by_query помощью?

Пробовал это:

 POST orders/_update_by_query
{
  "query": {
    "match_all": {}
  },
  "script": {
    "source": "ctx._source.new_d3_field",
    "lang": "painless",
    "type": "date",
    "format": "yyyy/MM/dd HH:mm:ss"
  }
}
  

Поле 2: Логическое поле с ? в имени

Мы хотим сохранить ? так, чтобы оно соответствовало другим полям, которые у нас уже есть в ES.

Также стоит отметить, что даже удаление ? и выполнение приведенного ниже поля не выглядит логическим значением.

Пробовал это:

 POST orders/_update_by_query
{
  "query": {
    "match_all": {}
  },
  "script": {
    "source": "ctx._source.new_b_field? = false",
    "lang": "painless"
  }
}
  

Что привело к ошибке:

 {
  "error" : {
    "root_cause" : [
      {
        "type" : "script_exception",
        "reason" : "compile error",
        "script_stack" : [
          "ctx._source.new_b_field? = false",
          "                         ^---- HERE"
        ],
        "script" : "ctx._source.new_b_field? = false",
        "lang" : "painless",
        "position" : {
          "offset" : 25,
          "start" : 0,
          "end" : 32
        }
      }
    ],
    "type" : "script_exception",
    "reason" : "compile error",
    "script_stack" : [
      "ctx._source.new_b_field? = false",
      "                         ^---- HERE"
    ],
    "script" : "ctx._source.new_b_field? = false",
    "lang" : "painless",
    "position" : {
      "offset" : 25,
      "start" : 0,
      "end" : 32
    },
    "caused_by" : {
      "type" : "illegal_argument_exception",
      "reason" : "invalid sequence of tokens near ['='].",
      "caused_by" : {
        "type" : "no_viable_alt_exception",
        "reason" : null
      }
    }
  },
  "status" : 400
}
  

Также пробовал:

 POST orders/_update_by_query?new_b_field?=false
  

Что дало:

 {
  "error" : {
    "root_cause" : [
      {
        "type" : "illegal_argument_exception",
        "reason" : "request [/orders/_update_by_query] contains unrecognized parameter: [new_b_field?]"
      }
    ],
    "type" : "illegal_argument_exception",
    "reason" : "request [/orders/_update_by_query] contains unrecognized parameter: [new_b_field?]"
  },
  "status" : 400
}
  

Ответ №1:

Если вы хотите добавить два новых поля в существующий индекс ElasticSearch, которые не имеют значения при создании, вам следует обновить его сопоставление с помощью Put mapping API

 PUT /orders/_mapping
{
  "properties": {
    "new_d3_field": {
      "type": "date",
      "format": "yyyy/MM/dd HH:mm:ss"
    },
    "new_b_field?": {
      "type": "boolean"
    }
  }
}
  

Если вы все еще хотите использовать _update_by_query , вам следует установить начальное значение, после чего поле будет добавлено.

 POST orders/_update_by_query?wait_for_completion=falseamp;conflicts=proceed
{
  "query": {
    "match_all": {}
  },
  "script": {
    "source": "ctx._source.new_d3_field=params.date;ctx._source.new_b_field = params.val",
    "lang": "painless",
    "params": {
      "date": "1980/01/01",
      "val": false
    }
  }
}
  

Обновление с помощью API запросов используется для обновления документов, поэтому, я думаю, вы не можете добавить поле в свою схему без обновления в списке один документ. что вы можете сделать, так это установить фиктивный документ и обновить только этот определенный документ. Что-то вроде этого:

 POST orders/_update_by_query
{
   "query": {
    "match": {
      "my-field":"my-value"
    }
  },
  "script": {
    "source": "ctx._source.new_d3_field=params.date;ctx._source.new_b_field = params.val",
    "lang": "painless",
    "params": {
      "date": "1980/01/01",
      "val": false
    }
  }
}