Reputation: 2936
With the 1.10 version of the .NET driver I could do something like this to get the max timestamp in the oplog collection:
this.oplogCollection.AsQueryable<OplogEntry>().Max(o => o.ts);
How can I do that with the new driver 2.0? The documentation is basically non-existent or not helpful, so I am hoping some insiders can shed some light here.
Upvotes: 9
Views: 11894
Reputation: 31282
Since MongoDB.Driver 2.0 the best approach is to use FindOptions
instance with specified Limit
and Sort
fields:
var options = new FindOptions<OplogEntry, OplogEntry>
{
Limit = 1,
Sort = Builders<OplogEntry>.Sort.Descending(o => o.ts)
};
var max = (await oplogCollection.FindAsync(FilterDefinition<OplogEntry>.Empty, options)).FirstOrDefault();
Sort
and Limit
params are processed on server side. Therefore such operation is very efficient with only one result item passed to the client.
Upvotes: 3
Reputation: 2936
Here's the quickest way to access the last entry in the oplog I have found so far:
this.oplogCollection.Find(new BsonDocument()).Sort(new BsonDocument("$natural", -1)).FirstOrDefaultAsync()
It sorts the oplog in reverse natural order and since the natural order in the oplog is by ascending timestamp, grabbing the last element gives me the max.
This method is very fast and from first experiments it does not seem dependent on the oplog size, since no actual sorting takes place.
The other solutions will decrease in performance with the size of the oplog.
Upvotes: 2
Reputation: 5773
You can try this:
var result = await collection.Find(x => true).SortByDescending(d => d.ts).Limit(1).FirstOrDefaultAsync();
BTW $max
doesn't give you the biggest value as in Linq or SQL, it specifies the upper exclusive bound of a Find
. Documentation here
Upvotes: 11
Reputation: 687
EDIT: Not sure if there is a better way, but this works. I haven't found a way to implement the $max operator easily.
var list = await collection.Aggregate().SortByDescending((a) => a["field"]).FirstAsync();
Upvotes: 6