Я использую Elasticsearch 2.3, и я пытаюсь выполнить двухэтапное вычисление с использованием агрегации конвейера. Меня интересует конечный результат агрегации конвейера, но Elasticsearch возвращает всю информацию о ведрах.Как выполнить агрегацию конвейера, не возвращая все ведра в Elasticsearch
Поскольку у меня огромное количество ведер (десятки или сотни миллионов), это непомерно. К сожалению, я не могу найти способ сказать Es не возвращать всю эту информацию.
Вот пример игрушки. У меня есть индекс test-index
с типом документа obj
. obj
имеет два поля: key
и values
.
curl -XPOST 'http://10.10.0.7:9200/test-index/obj' -d '{
"value": 100,
"key": "foo"
}'
curl -XPOST 'http://10.10.0.7:9200/test-index/obj' -d '{
"value": 20,
"key": "foo"
}'
curl -XPOST 'http://10.10.0.7:9200/test-index/obj' -d '{
"value": 50,
"key": "bar"
}'
curl -XPOST 'http://10.10.0.7:9200/test-index/obj' -d '{
"value": 60,
"key": "bar"
}'
curl -XPOST 'http://10.10.0.7:9200/test-index/obj' -d '{
"value": 70,
"key": "bar"
}'
Я хочу, чтобы получить среднее значение (по всем key
ы) минимальных value
в obj
с, имеющих одинаковые key
с. Среднее значение минимумов.
Elasticsearch позволяет мне это сделать:
curl -XPOST 'http://10.10.0.7:9200/test-index/obj/_search' -d '{
"size": 0,
"query": {
"match_all": {}
},
"aggregations": {
"key_aggregates": {
"terms": {
"field": "key",
"size": 0
},
"aggs": {
"min_value": {
"min": {
"field": "value"
}
}
}
},
"avg_min_value": {
"avg_bucket": {
"buckets_path": "key_aggregates>min_value"
}
}
}
}'
Но этот запрос возвращает минимальное значение для каждого ведра, хотя я и не нужен:
{
"took": 21,
"timed_out": false,
"_shards": {
"total": 5,
"successful": 5,
"failed": 0
},
"hits": {
"total": 4,
"max_score": 0,
"hits": [
]
},
"aggregations": {
"key_aggregates": {
"doc_count_error_upper_bound": 0,
"sum_other_doc_count": 0,
"buckets": [
{
"key": "bar",
"doc_count": 2,
"min_value": {
"value": 50
}
},
{
"key": "foo",
"doc_count": 2,
"min_value": {
"value": 20
}
}
]
},
"avg_min_value": {
"value": 35
}
}
}
Есть ли способ, чтобы избавиться от всей информации внутри "buckets": [...]
? Меня интересует только avg_min_value
.
Это может не показаться проблемой в этом примере игрушек, но когда число разных key
s не велико (десятки или сотни миллионов), ответ запроса является чрезмерно большим, и я бы хотел его обрезать.
Есть ли способ сделать это с помощью Elasticsearch? Или я неправильно моделирую свои данные?
NB: недопустимо предварительно агрегировать данные на ключ, поскольку часть моего запроса может быть заменена сложными и неизвестными фильтрами.
NB2: изменение size
на неотрицательное число в моем terms
агрегации неприемлемо, потому что это изменит результат.
Это кажется идеальным решением. Если бы мы это нашли! Мы не нашли прямого решения этой проблемы, поэтому мы приняли способ агрегации сценариев: построение карты, ключи которой являются полем «ключ», и значения минимумов по всем документам с заданным значением для «ключа» поля; затем агрегирование значений этой карты.Я не знаю, как они сравниваются с точки зрения производительности, но, по всей вероятности, ваше решение должно быть быстрее! – jrjd