Elasticsearch按嵌套字段分组

时间:2015-12-14 03:30:43

标签: java elasticsearch

有没有办法按嵌套字段分组并在非嵌套字段上执行聚合?

我在ES

中有这样的数据
{
    "_index": "bighalf",
    "_type": "excel",
    "_id": "AVE0rgXqe0-x669Gsae3",
    "_score": 1,
    "_source": {
      "Name": "Marsh",
      "date": "2015-11-07T10:47:14",
      "grade": 9,
      "year": 2016,
      "marks": 70,
      "subject": "Mathematics",
      "Gender": "male",
      "dob": "22/11/2000",
      "sprint": [
        {
          "sprintdate": "2015-11-06T22:30:00",
          "sprintname": "changed",
          "sprintpoints": 52
        }
      ]
    }
  },
  {
    "_index": "bighalf",
    "_type": "excel",
    "_id": "AVE0rvTHe0-x669Gsae5",
    "_score": 1,
    "_source": {
      "Name": "Taylor",
      "date": "2015-11-07T10:47:14",
      "grade": 9,
      "year": 2016,
      "marks": 54,
      "subject": "Mathematics",
      "Gender": "male",
      "dob": "22/11/2000",
      "sprint": [
        {
          "sprintdate": "2015-11-07T22:30:00",
          "sprintname": "jira",
          "sprintpoints": 52
        }
      ]
    }
  }

我希望按sprintname进行分组,找到marks

的总和

我试过这样:

SumBuilder sumGrades = AggregationBuilders.sum("sum_grade").field("grade");
NestedBuilder nested = AggregationBuilders.nested("nested").path("sprint")
.subAggregation(AggregationBuilders.terms("by_sprint").field("sprint.sprintname").subAggregation(sumGrades));
String names[] = { "changed", "jira" };
QueryBuilder query = QueryBuilders.boolQuery().must(
QueryBuilders.nestedQuery("sprint",QueryBuilders.boolQuery().must(QueryBuilders.termsQuery("sprint.sprintname", names))));
FilterAggregationBuilder aggregation = AggregationBuilders.filter("agg").filter(query).subAggregation(nested);

sum_grade对我不起作用。但是我使用嵌套字段(grade)更改了字段(sprintpoints)并且它有效但我的要求是找到sum("grade")并按sprint.sprintname分组。

1 个答案:

答案 0 :(得分:0)

由于您的sprint字段属于nested类型,因此在您的聚合中,您需要使用reverse_nested aggregation以便从嵌套文档中“跳回”根文档。它是这样的:

SumBuilder sumGrades = AggregationBuilders.sum("sum_grade").field("grade");

ReverseNestedBuilder backToGrades = AggregationBuilders.reverseNested("spring_to_grade")
    .subAggregation(sumGrades);

TermsBuilder bySprint = AggregationBuilders.terms("by_sprint")
    .field("sprint.sprintname").subAggregation(backToGrades)

NestedBuilder nested = AggregationBuilders.nested("nested").path("sprint")
    .subAggregation(bySprint);

String names[] = { "changed", "jira" };
QueryBuilder query = QueryBuilders.boolQuery().must(
QueryBuilders.nestedQuery("sprint",QueryBuilders.boolQuery().must(QueryBuilders.termsQuery("sprint.sprintname", names))));
FilterAggregationBuilder aggregation = AggregationBuilders.filter("agg").filter(query).subAggregation(nested);