【问题标题】:Nested aggregations in elasticsearchelasticsearch中的嵌套聚合
【发布时间】:2016-02-03 07:10:53
【问题描述】:

我正在尝试使用 elasticsearch 实现自动完成功能。我正在处理的索引结构是这样的

"title": "blog post 1",
"body": "body of the blog post",
"category": "programming",
"locations": [
    {"name": "united states"}, 
    {"name": "new york"}, 
    {"name": "venice"}
]

我正在尝试使用嵌套聚合。我正在使用的映射是这样的

{                            
  blog : {                   
    mappings : {             
      tag : {                
        properties : {       
          body : {           
            type : string    
          },                 
          category : {       
            type : string    
          },                 
          locations : {      
            properties : {   
              name : {       
                type : string
              }              
            }                
          },                 
          title : {          
            type : string    
          }                  
        }                    
      }                      
    }                        
  }                          
}

应该基于locations.name聚合结果的查询是

GET /blog/tag/_search
{
    "size": 0, 
    "query": {
        "match": {
            "locations.name": "montreal"
        }
    },
    "aggs": {
        "aggregated_locations": {
            "nested": {
                "path": "locations"
            },
            "aggs": {
                "filtered_locations": {
                   "terms": {
                      "fields": "locations.name"
                   }
                }
            }
        }
    }
}

目前我正在使用弹性搜索的 chrome 插件执行上述请求。上面的查询给出了一个错误,这个错误很长,但如果有人提示,我也可以发布它。我想我在解释嵌套聚合的含义时可能是错误的,这意味着我的映射是错误的。但我无法弄清楚问题出在哪里。

【问题讨论】:

    标签: elasticsearch elasticsearch-plugin


    【解决方案1】:

    您的映射中缺少一些部分,您需要将位置字段设置为nested 类型,并且不分析内部字段以便能够根据您的期望进行聚合:

    PUT blog
    {
      "mappings": {
        "tag": {
          "properties": {
            "body": {
              "type": "string"
            },
            "category": {
              "type": "string"
            },
            "locations": {
              "type": "nested",
              "properties": {
                "name": {
                  "type": "string",
                  "index": "not_analyzed"
                }
              }
            },
            "title": {
              "type": "string"
            }
          }
        }
      }
    }
    

    然后运行以下查询以过滤嵌套字段,并聚合嵌套字段:

    GET blog/_search
    {
      "size": 0, 
      "query": {
        "nested": {
          "path": "locations",
          "query": {
            "match": {
              "locations.name": "montreal"
            }
          }
        }
      },
      "aggs": {
        "aggregated_locations": {
          "nested": {
            "path": "locations"
          },
          "aggs": {
            "filtered": {
              "terms": {
                "field": "locations.name"
              }
            }
          }
        }
      }
    }
    

    这些查询可以被复制/粘贴(https://www.elastic.co/guide/en/sense/current/installing.html)

    【讨论】:

    • 我使用 --> curl -XGET 'localhost:9200/blog/_mapping/tag?pretty' >! test.json 来获取新的映射。但是 test.json 是一个巨大的文件。它有很多冗余。这是正常行为吗?
    • 所以我所做的是删除我的索引,运行映射,然后创建新的索引......我的工作流程有问题吗?我是弹性搜索的新手。
    • 您无法更新映射,工作流程正确,您需要先删除索引。有一篇博文在此处进行了解释 (elastic.co/blog/changing-mapping-with-zero-downtime),并指导如何以零停机时间进行操作。
    • 完全相同的映射和查询在我的 chrome 扩展中不起作用。使用上述指定的查询和映射是否需要 elasticsearch 2.0,我目前使用的是 elasticsearch 1.7
    • 如果找到查询中定义的特定位置,则查询返回位置列表中的所有元素。我只希望存储桶只有一个被查询的位置
    猜你喜欢
    • 2021-12-14
    • 2015-11-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-01-30
    • 2015-07-30
    • 2015-03-25
    相关资源
    最近更新 更多