【问题标题】:Elastic Search Unique Field Values弹性搜索唯一字段值
【发布时间】:2017-09-13 11:18:59
【问题描述】:

我正在尝试为搜索获取弹性搜索中的唯一值组。我无法弄清楚为什么这不起作用。

我已经解决了许多 StackOverflow 问题,并且大部分时间都在阅读文档。似乎没有什么对我有用,下面我提供了我最后尝试做的事情。

是否有人希望重复返回相同的结果?也许适用于不同版本的文档?


在本例中,我想要列出所有mfr_id 以及它们的mfr_desc。我在一个类型上运行它以仅搜索文档字段值。似乎 Agg 条款是实现此目的的方法,有人看到我做错了什么吗?


1:API 调用

GET /inventory/item/_search
{
  "size": 0,
  "_source": ["mfr_id", "mfr_desc"], 
  "aggs": {
    "unique_vals": {
      "terms": {
        "field": "mfr_id.keyword"  
        /** I have to use .keyword, seems like my mappings isn't working */
      }
    }
  }
}

2:映射文件

我在批量导入后运行的映射非常简单。如果您想要一个唯一的查询,我不会分析密钥:

{
  "index": "inventory",
  "body": {
    "settings": {
      "number_of_shards": 1
    },
    "mappings": {
      "_default_": {
        "properties": {
          "mfr_id": {
            "type": "string",
            "index": "not_analyzed"
          }
        }
      }
    }
  }
}

3:我的结果 当大约有 100 条记录时,聚合有大约 10 条记录。如果可能的话,我真的希望能够获得不仅仅是一个键的 _source 字段。

{
  "took": 3,
  "timed_out": false,
  "_shards": {
    "total": 1,
    "successful": 1,
    "failed": 0
  },
  "hits": {
    "total": 49341,
    "max_score": 0,
    "hits": []
  },
  "aggregations": {
    "unique_vals": {
      "doc_count_error_upper_bound": 0,
      "sum_other_doc_count": 6815,
      "buckets": [
        {
          "key": "14",
          "doc_count": 24292
        },
        {
          "key": "33",
          "doc_count": 5508
        },
        ...

【问题讨论】:

    标签: elasticsearch


    【解决方案1】:

    我真的希望能够获得超过 如果可能的话,只是一把钥匙。

    我想,你只有一个选择,我也遇到过同样的问题。试试这个:-

    {
        "aggregations": {
            "byId": {
                "terms": {
                    "field": "mfr_id"
                },
                "aggs": {
                    "byDesc": {
                        "terms": {
                            "field": "mfr_desc"
                        }
                    }
                }
            }
        }
    }
    

    现在您将在迭代 Elastic search JAVA API 时同时获得 id 和 desc。

    Terms aTerms = aAggregations.get("byId");
    aTerms.getBuckets().stream().forEach(aBucketById-> {
                Terms aTermsDesc = aBucketById.getAggregations().get("byDesc");
                aTermsDesc.getBuckets().stream().forEach(aBucketByDesc -> {
    //store id and desc
       });
    });
    

    【讨论】:

    • 哇,谢谢!我不会尝试这个。我很惊讶文档不清晰。它没有提供这样的例子;或者如果它确实存在,我找不到它。这很聪明,我想知道为什么这么简单的功能如此微不足道。此外,您的个人资料中的技能非常好。
    • 感谢您的夸奖 :)
    【解决方案2】:

    我会使用过滤器,它比聚合具有更好的性能。

    在聚合中,您将获得所有文档,并且仅在应用聚合时。如果您使用过滤器,您只会得到与过滤器匹配的文档,并且过滤器也可以被缓存。

    {
        "query": {
            "constant_score": {
                "filter": {
                    "exists": {
                        "field": "mfr_id"
                    }
                }
            }
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-11-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多