语法如下:
POST /company/_search
{
"aggs": {
"NAME": { //指定结果的名称
"AGG_TYPE": { //指定具体的聚合方法,
TODO: //# 聚合体内制定具体的聚合字段
}
}
TODO: //该处可以嵌套聚合
}
}
聚合分析功能主要有指标聚合、桶聚合、管道聚合和矩阵聚合,常用的有指标聚合和桶聚合,本文主要看一下指标聚合和桶聚合怎么使用。
指标聚合
对某个字段取最大值max
【sql】
select max(age) from company
【ES】
POST /company/_search
{
"aggs":{
"max_age":{
"max":{"field":"age"}
}
},
"size":0 //size=0是为了只看聚合结果
}
结果如下:
{
"aggregations": {
"max_age": {
"value": 64
}
}
}
elasticSearchRestTemplate java实现max
NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
MaxAggregationBuilder max =AggregationBuilders.max("maxAge").field("age");
queryBuilder.withAggregations(max);
SearchHits search = elasticSearchRestTemplate.search(queryBuilder.build(), DeviceInfo.class);
if (search.hasAggregations()) {
AggregationsContainer container = search.getAggregations();
Aggregations aggregations = (Aggregations) container.aggregations();
if (Objects.nonNull(aggregations)) {
Max maxAge= aggregations.get("maxAge");
log.info("计算 maxAge最大值:{} ", maxAge.getValue());
}
}
对某个字段取最小值min
【sql】
select min(age) from company
【ES】
POST /company/_search
{
"aggs":{
"min_age":{
"min":{"field":"age"}
}
},
"size":0
}
结果如下:
{
"aggregations": {
"min_age": {
"value": 1
}
}
}
java实现
NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
MinAggregationBuilder min =AggregationBuilders.min("minAge").field("age");
queryBuilder.withAggregations(min);
SearchHits search = elasticSearchRestTemplate.search(queryBuilder.build(), DeviceInfo.class);
if (search.hasAggregations()) {
AggregationsContainer container = search.getAggregations();
Aggregations aggregations = (Aggregations) container.aggregations();
if (Objects.nonNull(aggregations)) {
Min minAge= aggregations.get("minAge");
log.info("计算 minAge最小值:{} ", minAge.getValue());
}
}
分组查询统计并分页
【sql】
select p_key, count(running_state), count(use_state) from device_info group by p_key
【ES】POST /device_info/_search
{
"aggs": {
"pKey_groupby": {
"terms": {"field": "pKey"},
"aggs": {
"runningState_groupby": {
"terms": {"field": "runningState"}
},
"useState_groupby": {
"terms": {"field": "useState"}
},
"page":{
"bucket_sort": {
"from": 1,
"size": 3
}
}
}
}
},"size": 0
}
结果
java实现
NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
TermsAggregationBuilder pKeyAggregation = AggregationBuilders.terms("pKey").field("pKey");
TermsAggregationBuilder runningStateAggregation =AggregationBuilders.terms("runningState").field("runningState");
TermsAggregationBuilder useStateAggregation =AggregationBuilders.terms("useState").field("useState");
BucketSortPipelineAggregationBuilder bucket = new BucketSortPipelineAggregationBuilder("page",null).from(pageNum-1).size(pageSize);
pKeyAggregation.subAggregation(runningStateAggregation);
pKeyAggregation.subAggregation(useStateAggregation);
pKeyAggregation.subAggregation(bucket);
queryBuilder.withAggregations(pKeyAggregation);
NativeSearchQuery build = queryBuilder.build();
SearchHits search = elasticSearchRestTemplate.search(build, DeviceInfo.class);
Map<String,Integer> voMap = new HashMap<>();
if(search.hasAggregations()) {
AggregationsContainer container = search.getAggregations();
Aggregations aggregations = (Aggregations) container.aggregations();
Terms pTerms = aggregations.get("pKey");
int inx =0;
for (Terms.Bucket bk : pTerms.getBuckets()) {
DeviceBeanVo vo = new DeviceBeanVo();
String key = bk.getKeyAsString();
Integer cNum = Long.valueOf(bk.getDocCount()).intValue();
vo.setProductName(key);
vo.setAllNum(cNum);
vo.setYjh(0);
vo.setZx(0);
vo.setLx(0);
vo.setYqy(0);
Aggregations aggs = bk.getAggregations();
Terms rTerms = aggs.get("runningState");
for (Terms.Bucket r : rTerms.getBuckets()) {
String rKey = r.getKeyAsString();
Integer rNum = Long.valueOf(r.getDocCount()).intValue();
if(rKey.equals(RunStateEnum.YZX.getStatus().toString())){
vo.setYjh(vo.getYjh()+rNum);
vo.setZx(vo.getZx()+rNum);
}else if(rKey.equals(RunStateEnum.YLX.getStatus().toString())){
vo.setLx(vo.getLx()+rNum);
}
}
Terms uTerms = aggs.get("useState");
for (Terms.Bucket u : uTerms.getBuckets()) {
String uKey = u.getKeyAsString();
Integer uNum = Long.valueOf(u.getDocCount()).intValue();
if(uKey.equals(StateEnum.YFB.getStatus().toString())){
vo.setYqy(vo.getYqy()+uNum);
}
}
list.add(vo);
voMap.put(key,inx);
inx++;
}
}
复杂式查询
POST /device_info/_search
{
"aggs": {
"pKey_groupby": {
"terms": {
"field": "pKey"
},
"aggs": {
"pKey_top":{
"top_hits":{
"size": 1
}
},
"runningState_groupby": {
"terms": {
"field": "runningState"
}
},
"useState_groupby": {
"terms": {
"field": "useState"
}
},
"bucket_truncate": {
"bucket_sort": {
"from": 0,
"size": 10,
"sort": []
}
}
}
},
"pKey_distinct": {
"cardinality": {
"field": "pKey"
}
}
},"size": 0
}
java 实现
Integer pageNum = null==req.getPageNum()?1:req.getPageNum();
Integer pageSize = null==req.getPageSize()?10:req.getPageSize();
List<DeviceBeanVo> list = new ArrayList<>();
NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
ZngxUser user = SecurityUtils.getUser();
if(user.getFlag().equals("1")){
BoolQueryBuilder builder = QueryBuilders.boolQuery();
builder.must(QueryBuilders.termQuery("tenantId",user.getTenantId()));
queryBuilder.withQuery(builder);
}
Integer allNum = 0;
int start = (pageNum-1)*pageSize;
TermsAggregationBuilder pKeyAggregation = AggregationBuilders.terms("pKey").field("pKey");//要分组的字段
CardinalityAggregationBuilder pAllAggregation =AggregationBuilders.cardinality("pAll").field("pKey");//要distinct 统计的字段
TopHitsAggregationBuilder topAggregation=AggregationBuilders.topHits("device").size(1);//统计后匹配的一条数据
TermsAggregationBuilder runningStateAggregation =AggregationBuilders.terms("runningState").field("runningState");
TermsAggregationBuilder useStateAggregation =AggregationBuilders.terms("useState").field("useState");
BucketSortPipelineAggregationBuilder bucket = new BucketSortPipelineAggregationBuilder("page",null).from(start).size(pageSize);//桶分页
pKeyAggregation.subAggregation(topAggregation);
pKeyAggregation.subAggregation(runningStateAggregation);
pKeyAggregation.subAggregation(useStateAggregation);
pKeyAggregation.subAggregation(bucket);
queryBuilder.withAggregations(pKeyAggregation);
queryBuilder.withAggregations(pAllAggregation);
NativeSearchQuery build = queryBuilder.build();
SearchHits search = elasticSearchRestTemplate.search(build, DeviceInfo.class);
Set<String> kSet = new HashSet<>();
if(search.hasAggregations()) {
AggregationsContainer container = search.getAggregations();
Aggregations aggregations = (Aggregations) container.aggregations();
Terms pTerms = aggregations.get("pKey");
Cardinality cardinality = aggregations.get("pAll");
allNum=Long.valueOf(cardinality.getValue()).intValue();
for (Terms.Bucket bk : pTerms.getBuckets()) {
DeviceBeanVo vo = new DeviceBeanVo();
String key = bk.getKeyAsString();
kSet.add(key);
Integer cNum = Long.valueOf(bk.getDocCount()).intValue();
vo.setAllNum(cNum);
vo.setPKey(key);
vo.setYjh(0);
vo.setZx(0);
vo.setLx(0);
vo.setYqy(0);
Aggregations aggs = bk.getAggregations();
TopHits topHits = aggs.get("device");
org.elasticsearch.search.SearchHits hits =topHits.getHits();
org.elasticsearch.search.SearchHit hit =hits.getHits()[0];
DeviceInfo hitDev = BeanUtil.copyProperties(hit.getSourceAsMap(),DeviceInfo.class);
vo.setProductName(hitDev.getProductName());
Terms rTerms = aggs.get("runningState");
for (Terms.Bucket r : rTerms.getBuckets()) {
String rKey = r.getKeyAsString();
Integer rNum = Long.valueOf(r.getDocCount()).intValue();
if(rKey.equals(RunStateEnum.YZX.getStatus().toString())){
vo.setYjh(vo.getYjh()+rNum);
vo.setZx(vo.getZx()+rNum);
}else if(rKey.equals(RunStateEnum.YLX.getStatus().toString())){
vo.setLx(vo.getLx()+rNum);
}
}
Terms uTerms = aggs.get("useState");
for (Terms.Bucket u : uTerms.getBuckets()) {
String uKey = u.getKeyAsString();
Integer uNum = Long.valueOf(u.getDocCount()).intValue();
if(uKey.equals(StateEnum.YFB.getStatus().toString())){
vo.setYqy(vo.getYqy()+uNum);
}
}
list.add(vo);
}
}