在 spring-data-mongodb 中的 $last 聚合中返回对象

Returning object in $last aggregation in spring-data-mongodb

我想使用 spring-data-mongodb 实现以下查询:

db.getCollection('collection').aggregate([
{ $group: {_id: "$profile", last: { $last: { firstname:"$firstname", lastname:"$lastname"}}}}])

导致这样的结果:

{
  "_id": "",
  "last": {
            "firstname": "",
            "lastname": ""
          }
}

不过,似乎只有API可用

GroupOperation groupOperation = Aggregation.group("profile").last("firstname").as("firstname").last("lastname").as("lastname");

这转化为:

db.getCollection('collection').aggregate([
{ $group: {_id: "$profile", firstname: { $last: "$firstname"}, lastname: { $last: "$lastname"}}}])

给予:

{
  "_id": "",
  "firstname": "",
  "lastname": ""
}

GroupOperation.last(AggregationExpression expr)但不知道怎么用

另一方面,在一个聚合中多次使用 $last 是否会导致性能下降?

是的,当前 spring mongo 聚合助手的构造不允许这样做。但是你可以构造自己的"custom"聚合操作对象,然后在管道中使用:

public class CustomAggregationOperation implements AggregationOperation {
    private DBObject operation;

    public CustomAggregationOperation (DBObject operation) {
        this.operation = operation;
    }

    @Override
    public DBObject toDBObject(AggregationOperationContext context) {
        return context.getMappedObject(operation);
    }
}

这里的用法是:

    Aggregation agg = newAggregation(
      new CustomAggregationOperation(
        new BasicDBObject("$group",
            new BasicDBObject("last",
                new BasicDBObject("$last",
                    new BasicDBObject("fisrname","$firstname")
                        .append("lastname","$lastname")
                )
            )
        )
      )
    );

所以你可以只使用 BSON 对象构造函数来按照你想要的方式塑造管道阶段。这很高兴与 group()project() 以及所有其他辅助运算符混合,因为它实现了 AggregationOperation 接口。