当Spring数据Mongo中的用户聚合时,排序不起作用

时间:2014-11-27 02:20:28

标签: java mongodb spring-data aggregation-framework

我正在尝试在Spring数据上运行mongo聚合 这是json的样本

{
    "id":*****
    "taskResultContent":
    [
        {
            "executionUUID":"uuid_2",
            "sequency":"1",
            "returnContent":"SUCCESS",
        },
        {
            "executionUUID":"uuid_2",
            "sequency":"2",
            "returnContent":"SUCCESS",
        }
    ]
}

这是我的Mongo查询

[
    {
        "$match" : {
        "_id" : ObjectId("54767c7cfda0da01d4843e93")
        }
    },
    {
        "$unwind" : "$taskResultContent"
     },
    {
        "$project" : {
            "executionUUID" : "$taskResultContent.executionUUID",
            "returnContent" : "$taskResultContent.returnContent",
            "sequency" : "$taskResultContent.sequency",
            "_id" : 0,
            "resultID" : "$_id"
    }
    },
    {
        "$match" : {
        "executionUUID" : "uuid_3"
        }
    },
    {
        "$sort" : {
        "sequency" : -1
        }
    }
]

这是我的java实现:

Aggregation agg = newAggregation(
                match(Criteria.where("_id").is(objId)),
                unwind("taskResultContent"),
                project("taskResultContent.executionUUID","taskResultContent.returnContent","taskResultContent.sequency").and("resultID").previousOperation(),
                match(Criteria.where("executionUUID").is(executionUUID)),
                sort(DESC,"sequency")
            );

然后我发现了一个问题,SORT不起作用。 我从java打印出聚合查询。它看起来像:

    {
        "$sort": {
            "taskResultContent.sequency": -1
        }
    }

它应该是“sequerycy”: - 1但不是“taskResultContent.sequency”: - 1 有没有人遇到同样的问题?

2 个答案:

答案 0 :(得分:2)

你会成为新班级

class SortOperationEx implements AggregationOperation {

    private final Sort sort;

    /**
     * Creates a new {@link org.springframework.data.mongodb.core.aggregation.SortOperation} for the given {@link Sort} instance.
     *
     * @param sort must not be {@literal null}.
     */
    public SortOperationEx(Sort sort) {

        Assert.notNull(sort, "Sort must not be null!");
        this.sort = sort;
    }

    public SortOperationEx (Sort.Direction direction, String... fields) {
         this(new Sort(direction, fields));
    }

    public SortOperationEx and(Sort.Direction direction, String... fields) {
        return and(new Sort(direction, fields));
    }

    public SortOperationEx and(Sort sort) {
        return new SortOperationEx(this.sort.and(sort));
    }

    /*
     * (non-Javadoc)
     * @see org.springframework.data.mongodb.core.aggregation.AggregationOperation#toDBObject(org.springframework.data.mongodb.core.aggregation.AggregationOperationContext)
     */
    @Override
    public DBObject toDBObject(AggregationOperationContext context) {

        BasicDBObject object = new BasicDBObject();

        for (Sort.Order order : sort) {

            // Check reference
            String prop = order.getProperty();
            object.put(prop, order.isAscending() ? 1 : -1);
        }

        return new BasicDBObject("$sort", object);
    }
}

并修改代码来自:

Aggregation agg = newAggregation(
                match(Criteria.where("_id").is(objId)),
                unwind("taskResultContent"),
                project("taskResultContent.executionUUID","taskResultContent.returnContent","taskResultContent.sequency").and("resultID").previousOperation(),
                match(Criteria.where("executionUUID").is(executionUUID)),
                sort(DESC,"sequency")
            );

要:

Aggregation agg = newAggregation(
                match(Criteria.where("_id").is(objId)),
                unwind("taskResultContent"),                project("taskResultContent.executionUUID","taskResultContent.returnContent","taskResultContent.sequency").and("resultID").previousOperation(),
                match(Criteria.where("executionUUID").is(executionUUID)),
                 new SortOperationEx(DESC,"sequency")
            ); 

答案 1 :(得分:0)

修改您的项目阶段操作,以便通过其他名称将as()用于project字段,然后应用排序。

..
project("taskResultContent.executionUUID").as("executionUUID").
and("taskResultContent.returnContent").as("returnContent")
...