Агрегация Elasticsearch для извлечения массива значений, связанных с другим значением

#elasticsearch #elasticsearch-aggregation

#elasticsearch #elasticsearch-агрегация

Вопрос:

Я работаю с индексом Elasticsearch с такими данными:

 "_source": {
    "article_number": "123456",
    "title": "Example item #1",
    "attributes": [
        {
            "key": "Type",
            "value": "Bag"
        },
        {
            "key": "Color",
            "value": "Grey"
        }
    ]
},

"_source": {
    "article_number": "654321",
    "title": "Example item #2",
    "attributes": [
        {
            "key": "Type",
            "value": "Bag"
        },
        {
            "key": "Color",
            "value": "Red"
        }
    ]
}
 

Цель состоит в том, чтобы динамически генерировать поисковые входные данные на странице, где есть один поисковый ввод для каждого уникального значения attributes.key и внутри этого ввода одно значение для каждого соответствующего значения attributes.value . Поэтому в этом случае я хотел бы отобразить ввод «Типа», предлагающий только значение «Сумка», и ввод «Цвет», предлагающий значения «Серый» и «Красный».

Я пытаюсь выполнить это с помощью агрегации, которая даст мне уникальный набор всех значений attributes.key вместе с массивом всех значений attributes.value , которые связаны с каждым ключом. Примером результата, который соответствовал бы тому, на что я надеюсь, было бы следующее:

 {
    [
        {
            "key": "Type",
            "values": [{
                "name": "Bag",
                "doc_count": 2
            }]
        },
        {
            "key": "Color",
            "values": [{
                "name": "Grey",
                "doc_count": 1
            },
            {
                "name": "Red",
                "doc_count": 1
            }]
        }
}
 

Я пробовал вложенные и обратные вложенные агрегации, а также составные агрегации, но пока безуспешно.

Ответ №1:

Предполагая, что ваше отображение индекса выглядит следующим образом:

 PUT attrs
{
  "mappings": {
    "properties": {
      "attributes": {
        "type": "nested",
        "properties": {
          "key": {
            "type": "keyword"
          },
          "value": {
            "type": "keyword"
          }
        }
      }
    }
  }
}
 

вы можете достичь желаемых результатов с помощью следующей комбинации terms вложенной агрегации и ее подагрегации:

 POST attrs/_search
{
  "size": 0,
  "aggs": {
    "nested_context": {
      "nested": {
        "path": "attributes"
      },
      "aggs": {
        "by_keys": {
          "terms": {
            "field": "attributes.key",
            "size": 10
          },
          "aggs": {
            "by_values": {
              "terms": {
                "field": "attributes.value",
                "size": 10
              }
            }
          }
        }
      }
    }
  }
}
 

Комментарии:

1. Спасибо! Я действительно ценю это.

2. Добро пожаловать! Привет, кстати, я подробно рассказываю о практических примерах использования агрегации в моем руководстве по elasticsearch. Вы можете сообщить мне, какие (другие) темы вас интересуют, и я дам вам знать, как только выйдет руководство!