Агрегирование по фильтрам
Многогрупповое агрегирование, где каждая группа содержит документы, соответствующие запросу.
Пример:
resp = client.bulk(
index="logs",
refresh=True,
operations=[
{
"index": {
"_id": 1
}
},
{
"body": "warning: page could not be rendered"
},
{
"index": {
"_id": 2
}
},
{
"body": "authentication error"
},
{
"index": {
"_id": 3
}
},
{
"body": "warning: connection timed out"
}
],
)
print(resp)
resp1 = client.search(
index="logs",
size=0,
aggs={
"messages": {
"filters": {
"filters": {
"errors": {
"match": {
"body": "error"
}
},
"warnings": {
"match": {
"body": "warning"
}
}
}
}
}
},
)
print(resp1) response = client.bulk(
index: 'logs',
refresh: true,
body: [
{
index: {
_id: 1
}
},
{
body: 'warning: page could not be rendered'
},
{
index: {
_id: 2
}
},
{
body: 'authentication error'
},
{
index: {
_id: 3
}
},
{
body: 'warning: connection timed out'
}
]
)
puts response
response = client.search(
index: 'logs',
body: {
size: 0,
aggregations: {
messages: {
filters: {
filters: {
errors: {
match: {
body: 'error'
}
},
warnings: {
match: {
body: 'warning'
}
}
}
}
}
}
}
)
puts response const response = await client.bulk({
index: "logs",
refresh: "true",
operations: [
{
index: {
_id: 1,
},
},
{
body: "warning: page could not be rendered",
},
{
index: {
_id: 2,
},
},
{
body: "authentication error",
},
{
index: {
_id: 3,
},
},
{
body: "warning: connection timed out",
},
],
});
console.log(response);
const response1 = await client.search({
index: "logs",
size: 0,
aggs: {
messages: {
filters: {
filters: {
errors: {
match: {
body: "error",
},
},
warnings: {
match: {
body: "warning",
},
},
},
},
},
},
});
console.log(response1); PUT /logs/_bulk?refresh
{ "index" : { "_id" : 1 } }
{ "body" : "warning: page could not be rendered" }
{ "index" : { "_id" : 2 } }
{ "body" : "authentication error" }
{ "index" : { "_id" : 3 } }
{ "body" : "warning: connection timed out" }
GET logs/_search
{
"size": 0,
"aggs" : {
"messages" : {
"filters" : {
"filters" : {
"errors" : { "match" : { "body" : "error" }},
"warnings" : { "match" : { "body" : "warning" }}
}
}
}
}
} В приведенном примере мы анализируем сообщения журнала. Агрегирование создаст две группы (ведра) сообщений журнала: одну для всех сообщений, содержащих ошибку, и другую для всех, содержащих предупреждение.
Ответ:
{
"took": 9,
"timed_out": false,
"_shards": ...,
"hits": ...,
"aggregations": {
"messages": {
"buckets": {
"errors": {
"doc_count": 1
},
"warnings": {
"doc_count": 2
}
}
}
}
} Анонимные фильтры
Поле filters также может быть задано как массив фильтров, как в следующем запросе:
resp = client.search(
index="logs",
size=0,
aggs={
"messages": {
"filters": {
"filters": [
{
"match": {
"body": "error"
}
},
{
"match": {
"body": "warning"
}
}
]
}
}
},
)
print(resp) response = client.search(
index: 'logs',
body: {
size: 0,
aggregations: {
messages: {
filters: {
filters: [
{
match: {
body: 'error'
}
},
{
match: {
body: 'warning'
}
}
]
}
}
}
}
)
puts response const response = await client.search({
index: "logs",
size: 0,
aggs: {
messages: {
filters: {
filters: [
{
match: {
body: "error",
},
},
{
match: {
body: "warning",
},
},
],
},
},
},
});
console.log(response); GET logs/_search
{
"size": 0,
"aggs" : {
"messages" : {
"filters" : {
"filters" : [
{ "match" : { "body" : "error" }},
{ "match" : { "body" : "warning" }}
]
}
}
}
} Отфильтрованные группы возвращаются в том же порядке, что и в запросе. Ответ для этого примера будет:
{
"took": 4,
"timed_out": false,
"_shards": ...,
"hits": ...,
"aggregations": {
"messages": {
"buckets": [
{
"doc_count": 1
},
{
"doc_count": 2
}
]
}
}
}
Other Группа
Параметр other_bucket может быть установлен для добавления в ответ группы, содержащей все документы, не соответствующие ни одному из заданных фильтров. Значение этого параметра может быть следующим:
-
false - Не вычисляется группа
other -
true - Возвращает группу
other, либо в группе (с именем_other_по умолчанию), если используются именованные фильтры, либо как последнюю группу, если используются анонимные фильтры
Параметр other_bucket_key может использоваться для задания ключа для группы other, отличного от значения по умолчанию _other_. Установка этого параметра подразумевает установку параметра other_bucket в значение true.
Следующий фрагмент показывает ответ, в котором группа other запрошена с именем other_messages.
resp = client.index(
index="logs",
id="4",
refresh=True,
document={
"body": "info: user Bob logged out"
},
)
print(resp)
resp1 = client.search(
index="logs",
size=0,
aggs={
"messages": {
"filters": {
"other_bucket_key": "other_messages",
"filters": {
"errors": {
"match": {
"body": "error"
}
},
"warnings": {
"match": {
"body": "warning"
}
}
}
}
}
},
)
print(resp1) response = client.index(
index: 'logs',
id: 4,
refresh: true,
body: {
body: 'info: user Bob logged out'
}
)
puts response
response = client.search(
index: 'logs',
body: {
size: 0,
aggregations: {
messages: {
filters: {
other_bucket_key: 'other_messages',
filters: {
errors: {
match: {
body: 'error'
}
},
warnings: {
match: {
body: 'warning'
}
}
}
}
}
}
}
)
puts response const response = await client.index({
index: "logs",
id: 4,
refresh: "true",
document: {
body: "info: user Bob logged out",
},
});
console.log(response);
const response1 = await client.search({
index: "logs",
size: 0,
aggs: {
messages: {
filters: {
other_bucket_key: "other_messages",
filters: {
errors: {
match: {
body: "error",
},
},
warnings: {
match: {
body: "warning",
},
},
},
},
},
},
});
console.log(response1); PUT logs/_doc/4?refresh
{
"body": "info: user Bob logged out"
}
GET logs/_search
{
"size": 0,
"aggs" : {
"messages" : {
"filters" : {
"other_bucket_key": "other_messages",
"filters" : {
"errors" : { "match" : { "body" : "error" }},
"warnings" : { "match" : { "body" : "warning" }}
}
}
}
}
} Ответ будет примерно следующим:
{
"took": 3,
"timed_out": false,
"_shards": ...,
"hits": ...,
"aggregations": {
"messages": {
"buckets": {
"errors": {
"doc_count": 1
},
"warnings": {
"doc_count": 2
},
"other_messages": {
"doc_count": 1
}
}
}
}
} Ответ без ключей
По умолчанию агрегирование с именованными фильтрами возвращает группы как объект. Но в некоторых случаях сортировки, например, при использовании агрегирования сортировки ведер, порядок элементов в JSON не гарантируется. Можно использовать параметр keyed, чтобы указать группы как массив объектов. Значение этого параметра может быть следующим:
-
true - (По умолчанию) Возвращает группы как объект
-
false - Возвращает группы как массив объектов
Этот параметр игнорируется анонимными фильтрами.
Пример:
resp = client.search(
index="sales",
size="0",
filter_path="aggregations",
aggs={
"the_filter": {
"filters": {
"keyed": False,
"filters": {
"t-shirt": {
"term": {
"type": "t-shirt"
}
},
"hat": {
"term": {
"type": "hat"
}
}
}
},
"aggs": {
"avg_price": {
"avg": {
"field": "price"
}
},
"sort_by_avg_price": {
"bucket_sort": {
"sort": {
"avg_price": "asc"
}
}
}
}
}
},
)
print(resp) response = client.search(
index: 'sales',
size: 0,
filter_path: 'aggregations',
body: {
aggregations: {
the_filter: {
filters: {
keyed: false,
filters: {
"t-shirt": {
term: {
type: 't-shirt'
}
},
hat: {
term: {
type: 'hat'
}
}
}
},
aggregations: {
avg_price: {
avg: {
field: 'price'
}
},
sort_by_avg_price: {
bucket_sort: {
sort: {
avg_price: 'asc'
}
}
}
}
}
}
}
)
puts response const response = await client.search({
index: "sales",
size: 0,
filter_path: "aggregations",
aggs: {
the_filter: {
filters: {
keyed: false,
filters: {
"t-shirt": {
term: {
type: "t-shirt",
},
},
hat: {
term: {
type: "hat",
},
},
},
},
aggs: {
avg_price: {
avg: {
field: "price",
},
},
sort_by_avg_price: {
bucket_sort: {
sort: {
avg_price: "asc",
},
},
},
},
},
},
});
console.log(response); POST /sales/_search?size=0&filter_path=aggregations
{
"aggs": {
"the_filter": {
"filters": {
"keyed": false,
"filters": {
"t-shirt": { "term": { "type": "t-shirt" } },
"hat": { "term": { "type": "hat" } }
}
},
"aggs": {
"avg_price": { "avg": { "field": "price" } },
"sort_by_avg_price": {
"bucket_sort": { "sort": { "avg_price": "asc" } }
}
}
}
}
} Ответ:
{
"aggregations": {
"the_filter": {
"buckets": [
{
"key": "t-shirt",
"doc_count": 3,
"avg_price": { "value": 128.33333333333334 }
},
{
"key": "hat",
"doc_count": 3,
"avg_price": { "value": 150.0 }
}
]
}
}
}
© 2023-2025 Elasticsearch
As of September 2024, Elasticsearch is available under a choice of three licenses: the Server Side Public License (SSPL), the Elastic License, or the AGPLv3 (OSI approved).
Elasticsearch and the Elasticsearch logo are trademarks of Elasticsearch B.V., registered in the U.S. and in other countries.
https://www.elastic.co/guide/en/elasticsearch/reference/8.17/search-aggregations-bucket-filters-aggregation.html