Elasticsearch将过滤器应用于聚合

时间:2016-09-29 05:59:16

标签: elasticsearch

我尝试使用Elasticsearch构建一个facet系统,以显示与查询匹配的文档数。

我目前正在/_search?search_type=count上执行此查询:

{
    "query": {
        "query_string": {
            "query": "status:(1|2) AND categories:A"
        }
    },
    "aggs": {
        "all_products": {
            "global": {},
            "aggs": {
                "countries": {
                    "aggs": {
                        "counter": {
                            "terms": ["min_doc_count": 0, "field": "country"],
                            "aggs": ["unique": ["cardinality": ["field": "id"]]]
                        }
                    }
                },
                "categories": {
                    "aggs": {
                        "counter": {
                            "terms": ["min_doc_count": 0, "field": "category"],
                            "aggs": ["unique": ["cardinality": ["field": "id"]]]
                        }
                    }
                },
                "statuses": {
                    "aggs": {
                        "counter": {
                            "terms": ["min_doc_count": 0, "field": "status"],
                            "aggs": ["unique": ["cardinality": ["field": "id"]]]
                        }
                    }
                }
            }
        }
    }
}

文件具有以下结构:

{
    "id": 123,
    "name": "Title",
    "categories": ["A", "B", "C"],
    "country": "United Kingdom",
    "status": 1
}

所以我要找的输出应该是:

国家

  • 英国:123
  • 美国:1000

分类

  • Motors:23
  • 时装:1100

状态

  • 活跃:1120
  • 不活跃:3

我不知道如何正确过滤聚合,因为现在他们正在计算指定字段中的所有文档,而不考虑查询status:(1|2) AND categories:A

弹性版本是1.7.2。

2 个答案:

答案 0 :(得分:0)

您只需删除global聚合,因为它不受查询的影响,只需将您的countriescategoriesstatuses聚合移到顶层,就像这样:

{
    "query": {
        "query_string": {
            "query": "status:(1|2) AND categories:A"
        }
    },
    "aggs": {
            "countries": {
                "aggs": {
                    "counter": {
                        "terms": ["min_doc_count": 0, "field": "country"],
                        "aggs": ["unique": ["cardinality": ["field": "id"]]]
                    }
                }
            },
            "categories": {
                "aggs": {
                    "counter": {
                        "terms": ["min_doc_count": 0, "field": "category"],
                        "aggs": ["unique": ["cardinality": ["field": "id"]]]
                    }
                }
            },
            "statuses": {
                "aggs": {
                    "counter": {
                        "terms": ["min_doc_count": 0, "field": "status"],
                        "aggs": ["unique": ["cardinality": ["field": "id"]]]
                    }
                }
            }
        }

}

答案 1 :(得分:0)

法比奥。我看到你上传的帖子,我已经为ES 2.4做过例子,可能对你有帮助。

    "index": "{{YOUR ELASTIC INDEX}}",
    "type": "{{YOUR ELASTIC TYPE}}",
    "body": {
        "aggs": {
            "trademarks": { // aggs NAME
                "terms": {
                    "field": "id",   // field name in ELASTIC base
                    "size": 100  // count of results YOU need
                }
            },
            "materials": { //another aggs NAME
                "terms": {  
                    "field": "materials.name", // field name in ELASTIC base
                    "size": 100 / count of results YOU need
                }
            },
            "certificate": { 
                "terms": {
                    "field": "certificate_type_id",
                    "size": 100
                }
            },
            "country": {
                "terms": {
                    "field": "country.id",
                    "size": 100
                }
            },
            "price": {
                "stats": {
                    "field": "price"
                }
            }
        },
        "from": 0,  // start from
        "size": 20, // results count
        "query": {
            "constant_score": {
                "filter": {  //apply filter
                    "bool": {
                        "should": [{   // all categories You need to show
                            "term": {
                                "categories": "10142" 
                            }
                        }, {
                            "term": {
                                "categories": "10143"
                            }
                        }, {
                            "term": {
                                "categories": "10144"
                            }
                        }, {
                            "term": {
                                "categories": "10145"
                            }
                        }, {
                            "term": {
                                "categories": "12957"
                            }
                        }, {
                            "term": {
                                "categories": "13968"
                            }
                        }, {
                            "term": {
                                "categories": "14353"
                            }
                        }, {
                            "term": {
                                "categories": "16954"
                            }
                        }, {
                            "term": {
                                "categories": "18243"
                            }
                        }, {
                            "term": {
                                "categories": "10141"
                            }
                        }],
                        "must": [{  // if you want another filed to filter for example filter BY field trademark_id
                            "bool": {
                                "should": [{
                                    "term": {
                                        "trademark_id": "2872"
                                    }
                                }, {
                                    "term": {
                                        "trademark_id": "2879"
                                    }
                                }, {
                                    "term": {
                                        "trademark_id": "2914"
                                    }
                                }]
                            }
                        }, {
                            "bool": {  // filter by PRICE
                                "must": [{
                                    "range": {
                                        "price": {
                                            "from": 5.97,
                                            "to": 15752.69
                                        }
                                    }
                                }]
                            }
                        }]
                    }
                }
            }
        },
        "sort": {  //here SORT BY desc or asc
            "updated_at": "desc" //updated_at -  field from ES base
        }
    }