Как использовать значение вложенных документов в оценке скриптов - PullRequest
0 голосов
/ 07 октября 2019

Схема выглядит следующим образом:

  "mappings": {
    "_doc": {
      "_all": {
        "enabled": false
      },
      "properties": {
        "category_boost": {
          "type": "nested",
          "properties" : {
            "category": {
              "type": "text",
              "index": false
            },
            "boost": {
              "type": "integer",
              "index": false
            }
          }
        }
      }
    }
  }

Документ в эластичном формате имеет данные:

    "category_boost": [
        {
            "category": "A",
            "boost": 98
        },
        {
            "category": "B",
            "boost": 96
        },
        {
            "category": "C",
            "boost": 94
        },
    ],

Функция внутренней оценки:

for (int i=0; i<doc['"'category_boost.boost'"'].size(); ++i) {
    if (doc['"'category_boost.category'"'][i].value.equals(params.category)) {
        boost = doc['"'category_boost.boost'"'][i].value;
    }
}

Также пробовал length, чтобы получить размер массива, но помогло. Так как это не влияет на результаты, я попытался разделить на size(), и это дает ошибку деления на ноль, поэтому я пришел к выводу, что размер равен 0.

Общая проблема : есть картаcategory-> boost, который является динамическим, и я не могу жестко закодировать в схему. Я попытался набрать object с объектом json, но оказалось, что вы не можете получить доступ к этим объектам в функциях скоринга, поэтому я использовал массивы с определенными типами.

1 Ответ

0 голосов
/ 08 октября 2019

вложенный тип данных создает поддокументы для представления элементов ваших коллекций. Так что доступ к их значениям документа в скрипте возможен, но вы должны быть внутри вложенного запроса.

Вот один из способов сделать это, я надеюсь, что он соответствует вашим требованиям. В этом примере возвращается только документ с оценкой в ​​зависимости от выбранной категории.

Примечание: я использовал эластичный поиск 7 в своей локальной сети, поэтому вам придется изменить отображение, чтобы добавить запись "_doc" и т. Д.

ЗдесьВ измененном отображении я удалил index: false во вложенных свойствах, поскольку теперь мы используем их в запросах

PUT test-score_nested
{
  "mappings": {
    "properties": {
      "category_boost": {
        "type": "nested",
        "properties": {
          "category": {
            "type": "keyword"
          },
          "boost": {
            "type": "integer"
          }
        }
      }
    }
  }
}

Затем я добавляю ваши образцы данных:

POST test-score_nested/_doc
{
  "category_boost": [
        {
            "category": "A",
            "boost": 98
        },
        {
            "category": "B",
            "boost": 96
        },
        {
            "category": "C",
            "boost": 94
        }
    ]
}

И затем запрос.

  1. Мы углубляемся на один уровень во вложенной коллекции
  2. Внутри коллекции мы используем запрос оценки функции с режимом замены
  3. Внутри оценки функции мы используемзапрос фильтра, чтобы «выбрать» хорошую категорию и использовать ее повышение для оценки

POST test-score_nested/_search
{
  "query": {
    "nested": {
      "path": "category_boost",
      "query": {
        "function_score": {
          "boost_mode": "replace", 
          "query": {
            "term": {
              "category_boost.category": {
                "value": "A"
              }
            }
          },
          "functions": [
            {
              "field_value_factor": {
                "field": "category_boost.boost"
              }
            }
          ]
        }
      }
    }
  }
}

возвращает

{
  "took" : 0,
  "timed_out" : false,
  "_shards" : {
    "total" : 1,
    "successful" : 1,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 1,
      "relation" : "eq"
    },
    "max_score" : 98.0,
    "hits" : [
      {
        "_index" : "test-score_nested",
        "_type" : "_doc",
        "_id" : "v3Smqm0BZ7nyeX7PPevA",
        "_score" : 98.0,
        "_source" : {
          "category_boost" : [
            {
              "category" : "A",
              "boost" : 98
            },
            {
              "category" : "B",
              "boost" : 96
            },
            {
              "category" : "C",
              "boost" : 94
            }
          ]
        }
      }
    ]
  }
}

Надеюсь, это поможет вам!

...