弹性搜索按嵌套文档的计数过滤

时间:2015-10-24 10:09:54

标签: elasticsearch

我有一个公司的弹性搜索索引,它有一个名为 transactions 的嵌套对象。交易至少包含日期字段。这是一个示例:

firms: [
  {
    "name": "abc",
    "address" : "xyz",
    "transactions": [
       {
         "date" : "2014-12-20"
         "side" : "buyer"
       },
       ...
     ]
  },
  ...
]

根据这些数据,我想查询过去6或12个月内有(比方说)3次以上交易的所有公司。

以下查询返回过去12个月内至少有一笔交易的公司:

POST firms/firm/_search
    {
    "query": {
        "nested": {
           "path": "transactions",
           "query": {
               "bool": {
                   "must": [
                      {
                          "match": {
                             "transactions.side": "buyer"
                          }
                      },
                      {
                          "range": {
                             "transactions.date": {
                                "from": "2014-10-24",
                                "to": "2015-10-24"
                             }
                          }
                      }
                   ]
               }
           }
        }  
    }
}

我不确定如何扩展此查询以匹配在y +月内具有x +交易的公司。任何帮助将不胜感激。感谢

1 个答案:

答案 0 :(得分:2)

我认为除了使用public static void main(String[] args) { Myclass m = new Myclass(); Set<Myclass> set = new HashSet<>(); set.add(m); System.out.println(set.contains(m)); } 之外,您还有其他选择。像这样:

script

对于那些日期都不匹配的文档,实际的{ "query": { "bool": { "must": [ { "nested": { "path": "transactions", "query": { "bool": { "must": [ { "match": { "transactions.side": "buyer" } }, { "range": { "transactions.date": { "from": "2014-10-24", "to": "2015-10-24" } } } ] } } } }, { "filtered": { "filter": { "script": { "script": "if(_source.transactions.size<3) return false;fromDate=Date.parse('yyyy-MM-dd',fromDateParam);toDate=Date.parse('yyyy-MM-dd',toDateParam);count=0;for(d in _source.transactions){docsDate=Date.parse('yyyy-MM-dd',d.get('date'));if(docsDate>=fromDate && docsDate<=toDate){count++};if(count==3){return true;}};return false;", "params": { "fromDateParam":"2014-10-24", "toDateParam":"2015-10-24" } } } } } ] } } } 过滤器是“优化”。因此,此文档(范围内没有日期)将无法访问成本更高的range过滤器。

script本身首先检查交易数是否小于script。如果是,请不要打扰进行所有日期检查并返回3。如果它超过false,则取每个日期并与参数进行比较。一旦达到3的计数,请停止查看其余日期并返回3