[JAVA-2471] aggregation on view doesn't work Created: 16/Mar/17  Updated: 04/Apr/17  Resolved: 04/Apr/17

Status: Closed
Project: Java Driver
Component/s: Query Operations
Affects Version/s: 3.4.2
Fix Version/s: 3.5.0

Type: Improvement Priority: Major - P3
Reporter: adrien petel Assignee: Jeffrey Yemin
Resolution: Done Votes: 0
Labels: None
Remaining Estimate: Not Specified
Time Spent: Not Specified
Original Estimate: Not Specified
Environment:

ubuntu 16.04, single mongod instance, no shard, no replica set. Used along with spring-data-mongodb 1.10.1


Attachments: Java Source File JAVA2471.java    

 Description   

Aggregation on view doesn't work when run with java driver, but works fine in shell.

sample code to reproduce the issue:

 
MongoClient client = new MongoClient("localhost", 27017);
SimpleMongoDbFactory factory = new SimpleMongoDbFactory(client, "databaseName");
MongoTemplate mongoTemplate = new MongoTemplate(factory);
List<DBObject> pipeline = new ArrayList<>();
BasicDBObject sort = new BasicDBObject("$sort", new BasicDBObject("_id", 1));
pipeline.add(sort);
 
AggregationOutput output = mongoTemplate.getCollection("viewCollection").aggregate(pipeline);
for (DBObject obj : output.results()) {
   String id = (String) obj.get("_id");
   System.out.println("ID IS " + id);
}

Error shows up with both Cursor and AggregationOutput

stack trace:

Exception in thread "main" org.bson.BsonInvalidOperationException: Document does not contain key result
at org.bson.BsonDocument.throwIfKeyAbsent(BsonDocument.java:844)
at org.bson.BsonDocument.getArray(BsonDocument.java:147)
at com.mongodb.operation.BsonDocumentWrapperHelper.toList(BsonDocumentWrapperHelper.java:28)
at com.mongodb.operation.AggregateOperation.createQueryResult(AggregateOperation.java:356)
at com.mongodb.operation.AggregateOperation.access$700(AggregateOperation.java:67)
at com.mongodb.operation.AggregateOperation$3.apply(AggregateOperation.java:367)
at com.mongodb.operation.AggregateOperation$3.apply(AggregateOperation.java:364)
at com.mongodb.operation.CommandOperationHelper.executeWrappedCommandProtocol(CommandOperationHelper.java:216)
at com.mongodb.operation.CommandOperationHelper.executeWrappedCommandProtocol(CommandOperationHelper.java:207)
at com.mongodb.operation.CommandOperationHelper.executeWrappedCommandProtocol(CommandOperationHelper.java:113)
at com.mongodb.operation.AggregateOperation$1.call(AggregateOperation.java:257)
at com.mongodb.operation.AggregateOperation$1.call(AggregateOperation.java:253)
at com.mongodb.operation.OperationHelper.withConnectionSource(OperationHelper.java:431)
at com.mongodb.operation.OperationHelper.withConnection(OperationHelper.java:404)
at com.mongodb.operation.AggregateOperation.execute(AggregateOperation.java:253)
at com.mongodb.operation.AggregateOperation.execute(AggregateOperation.java:67)
at com.mongodb.Mongo.execute(Mongo.java:836)
at com.mongodb.Mongo$2.execute(Mongo.java:823)
at com.mongodb.DBCollection.aggregate(DBCollection.java:1455)
at com.mongodb.DBCollection.aggregate(DBCollection.java:1380)
at com.mongodb.DBCollection.aggregate(DBCollection.java:1366)
at com.mycompany.test.Main.main(Main.java:200)



 Comments   
Comment by Githook User [ 04/Apr/17 ]

Author:

{u'username': u'jyemin', u'name': u'Jeff Yemin', u'email': u'jeff.yemin@10gen.com'}

Message: JAVA-2471: Recognize cursor field in the reply to an aggregate command even if inline results were requested.
Branch: master
https://github.com/mongodb/mongo-java-driver/commit/c6300f2c5476f894f460993168265041498a6e5e

Comment by Ross Lawley [ 16/Mar/17 ]

felix2626, having discussed internally, we think we can improve the current the experience in the next release (3.5.0). I'll also update the type from bug to improvement.

Comment by Ross Lawley [ 16/Mar/17 ]

As in the driver can't tell if the underlying collection is a view and because the inline results are being deprecated. I'm marking this as won't fix.

Comment by Ross Lawley [ 16/Mar/17 ]

This is a side effect of how views work, aggregations returned from views always come back as cursors. However, in the legacy API it defaults to inline results and this is why you are seeing an error. Inline results for the aggregate command were deprecated in the server for MongoDB 3.4 and will be removed in MongoDB 3.6 (JAVA-2442, JAVA-2443). To fix you must return a cursor when aggregating against views.

By default in 3.4.2 DBCollection.aggregate(pipeline) sets the output mode to be OutputMode.INLINE and this is the cause of the error. The work done in JAVA-2443 deprecates these methods and deprecates OutputMode.
Changing your aggregation code to:

Cursor cursor = legacyCollection.aggregate(pipeline, AggregationOptions.builder().outputMode(AggregationOptions.OutputMode.CURSOR).build());

Will fix the issue. I attached a test case showing the issue succeeds when using the cursor output mode but fails with the default.

Ross

Generated at Thu Feb 08 08:57:18 UTC 2024 using Jira 9.7.1#970001-sha1:2222b88b221c4928ef0de3161136cc90c8356a66.