在一次聚合 Spring 引导中动态地进行多个平均
Dynamically multiple averages in one Aggregation Spring Boot
我一直在尝试使用 Spring boot Aggregation 按标识符分组多个平均值。我想要的平均值的字段由参数给定的数组定义,但我无法检索多个平均值。
数据存储如下:
{
"_id": {
"$oid": "XX"
},
"space_id": "AA",
"temperature": 50,
"temperatureUoMCode": 0,
"pm25": 50,
"pm25UoMCode": 0,
"co2": 0.0005,
"co2UoMCode": 0,
"co": 1,
"coUoMCode": 0,
"gas": 50,
"gasUoMCode": 0,
"humidity": 50,
"humidityUoMCode": 0,
"occupants": 6,
"maxCapacity": 15,
"_class": "Record"
}
我使用的代码:
List<AggregationOperation> aggregationOperations = new ArrayList<>();
aggregationOperations.add(Aggregation.match(
Criteria.where("space_id").is(space_id)
));
for(Variable var : concerns){
System.out.println(var.getField());
aggregationOperations.add(Aggregation.group(
space_id).
avg(var.getField()).as(var.getAvg()));
}
Aggregation aggregation = Aggregation.newAggregation(
aggregationOperations
);
AggregationResults<HashMap> results = mongoTemplate.aggregate(
aggregation, "records",HashMap.class);
另外,变量class是一个枚举,有两个字段,db中的字段名(field)和平均别名(avg)。
当我 运行 它时,我得到以下输出:
co
pm25
temperature
humidity
gas
2021-09-22 11:34:17.046 ERROR 42971 --- [a1-0b2af6e69097] TConfig$$EnhancerBySpringCGLIB$3c396b : Invalid reference 'pm25'!
java.lang.IllegalArgumentException: Invalid reference 'pm25'!
at org.springframework.data.mongodb.core.aggregation.ExposedFieldsAggregationOperationContext.getReference(ExposedFieldsAggregationOperationContext.java:114)
at org.springframework.data.mongodb.core.aggregation.ExposedFieldsAggregationOperationContext.getReference(ExposedFieldsAggregationOperationContext.java:86)
at org.springframework.data.mongodb.core.aggregation.GroupOperation$Operation.getValue(GroupOperation.java:529)
at org.springframework.data.mongodb.core.aggregation.GroupOperation$Operation.toDocument(GroupOperation.java:507)
at org.springframework.data.mongodb.core.aggregation.GroupOperation.toDocument(GroupOperation.java:441)
at org.springframework.data.mongodb.core.aggregation.AggregationOperation.toPipelineStages(AggregationOperation.java:55)
at org.springframework.data.mongodb.core.aggregation.AggregationOperationRenderer.toDocument(AggregationOperationRenderer.java:56)
at org.springframework.data.mongodb.core.aggregation.AggregationPipeline.toDocuments(AggregationPipeline.java:81)
at org.springframework.data.mongodb.core.aggregation.Aggregation.toPipeline(Aggregation.java:716)
at org.springframework.data.mongodb.core.AggregationUtil.createPipeline(AggregationUtil.java:112)
at org.springframework.data.mongodb.core.MongoTemplate.doAggregate(MongoTemplate.java:2144)
at org.springframework.data.mongodb.core.MongoTemplate.doAggregate(MongoTemplate.java:2119)
at org.springframework.data.mongodb.core.MongoTemplate.aggregate(MongoTemplate.java:2113)
at org.springframework.data.mongodb.core.MongoTemplate.aggregate(MongoTemplate.java:2014)
at co.edu.javeriana.smartuj.EnvironmentalAlerts.services.AlertService.makeQuery(AlertService.java:131)
如果有人遇到类似的问题,我按照 设法解决了。我意识到,与其创建各种 GroupOperations,不如创建一个并使用它来存储所有操作,方法是将“as”函数的 return 保存在同一个对象中:
MatchOperation matchOperation = Aggregation.match(Criteria.where("space_id").is(space_id));
GroupOperation groupOperation = null;
for(Variable var : concerns){
if (groupOperation == null){
groupOperation = Aggregation.group("space_id")
.avg(var.getField())
.as(var.getAvg());
}else
groupOperation = groupOperation
.avg(var.getField())
.as(var.getAvg());
}
Aggregation aggregation = Aggregation.newAggregation(
matchOperation,
groupOperation
);
AggregationResults<HashMap> results = mongoTemplate.aggregate(
aggregation, "records",HashMap.class);
return results.getUniqueMappedResult();
我一直在尝试使用 Spring boot Aggregation 按标识符分组多个平均值。我想要的平均值的字段由参数给定的数组定义,但我无法检索多个平均值。 数据存储如下:
{
"_id": {
"$oid": "XX"
},
"space_id": "AA",
"temperature": 50,
"temperatureUoMCode": 0,
"pm25": 50,
"pm25UoMCode": 0,
"co2": 0.0005,
"co2UoMCode": 0,
"co": 1,
"coUoMCode": 0,
"gas": 50,
"gasUoMCode": 0,
"humidity": 50,
"humidityUoMCode": 0,
"occupants": 6,
"maxCapacity": 15,
"_class": "Record"
}
我使用的代码:
List<AggregationOperation> aggregationOperations = new ArrayList<>();
aggregationOperations.add(Aggregation.match(
Criteria.where("space_id").is(space_id)
));
for(Variable var : concerns){
System.out.println(var.getField());
aggregationOperations.add(Aggregation.group(
space_id).
avg(var.getField()).as(var.getAvg()));
}
Aggregation aggregation = Aggregation.newAggregation(
aggregationOperations
);
AggregationResults<HashMap> results = mongoTemplate.aggregate(
aggregation, "records",HashMap.class);
另外,变量class是一个枚举,有两个字段,db中的字段名(field)和平均别名(avg)。 当我 运行 它时,我得到以下输出:
co
pm25
temperature
humidity
gas
2021-09-22 11:34:17.046 ERROR 42971 --- [a1-0b2af6e69097] TConfig$$EnhancerBySpringCGLIB$3c396b : Invalid reference 'pm25'!
java.lang.IllegalArgumentException: Invalid reference 'pm25'!
at org.springframework.data.mongodb.core.aggregation.ExposedFieldsAggregationOperationContext.getReference(ExposedFieldsAggregationOperationContext.java:114)
at org.springframework.data.mongodb.core.aggregation.ExposedFieldsAggregationOperationContext.getReference(ExposedFieldsAggregationOperationContext.java:86)
at org.springframework.data.mongodb.core.aggregation.GroupOperation$Operation.getValue(GroupOperation.java:529)
at org.springframework.data.mongodb.core.aggregation.GroupOperation$Operation.toDocument(GroupOperation.java:507)
at org.springframework.data.mongodb.core.aggregation.GroupOperation.toDocument(GroupOperation.java:441)
at org.springframework.data.mongodb.core.aggregation.AggregationOperation.toPipelineStages(AggregationOperation.java:55)
at org.springframework.data.mongodb.core.aggregation.AggregationOperationRenderer.toDocument(AggregationOperationRenderer.java:56)
at org.springframework.data.mongodb.core.aggregation.AggregationPipeline.toDocuments(AggregationPipeline.java:81)
at org.springframework.data.mongodb.core.aggregation.Aggregation.toPipeline(Aggregation.java:716)
at org.springframework.data.mongodb.core.AggregationUtil.createPipeline(AggregationUtil.java:112)
at org.springframework.data.mongodb.core.MongoTemplate.doAggregate(MongoTemplate.java:2144)
at org.springframework.data.mongodb.core.MongoTemplate.doAggregate(MongoTemplate.java:2119)
at org.springframework.data.mongodb.core.MongoTemplate.aggregate(MongoTemplate.java:2113)
at org.springframework.data.mongodb.core.MongoTemplate.aggregate(MongoTemplate.java:2014)
at co.edu.javeriana.smartuj.EnvironmentalAlerts.services.AlertService.makeQuery(AlertService.java:131)
如果有人遇到类似的问题,我按照
MatchOperation matchOperation = Aggregation.match(Criteria.where("space_id").is(space_id));
GroupOperation groupOperation = null;
for(Variable var : concerns){
if (groupOperation == null){
groupOperation = Aggregation.group("space_id")
.avg(var.getField())
.as(var.getAvg());
}else
groupOperation = groupOperation
.avg(var.getField())
.as(var.getAvg());
}
Aggregation aggregation = Aggregation.newAggregation(
matchOperation,
groupOperation
);
AggregationResults<HashMap> results = mongoTemplate.aggregate(
aggregation, "records",HashMap.class);
return results.getUniqueMappedResult();