Reputation: 1088
I have done the paging implementation using the following:
.Find(_ => true).Skip(PageSize * (int)(PageNumber - 1)).Limit(PageSize).ToListAsync().Result;
and inside of the paging code I have called DeleteOneAsync( with _id filter), I have over 5,00,000 records and the paging working fine, just that the delete api doesn't delete all the records as expected. My pseudo-code is as follows:
while(true)
{
var page = GetPage(pageIdx++); //starts with 1
if(page.Count == 0)
break;
foreach(var p in page)
{
Delete(p);
}
}
There is no error raised anywhere, all the processing runs fine, but at the ends I expect all records to be deleted but I see that only a few chunk is deleted. Any clue why this happens or if there is a issue in paging part of mine?
Sample code:
public static class ConsoleProgram
{
const int PAGE_SIZE = 100;
public static void Main(string[] args)
{
MongoClientSettings clientSettings = new MongoClientSettings();
clientSettings.Server = new MongoServerAddress("localhost", 27017);
MongoDB.Driver.MongoClient client = new MongoDB.Driver.MongoClient(clientSettings);
IMongoDatabase db = client.GetDatabase("petrel");
IMongoCollection<BsonDocument> mt = db.GetCollection<BsonDocument>("PatientDocuments");
int pageNo = 1;
int count = 0;
while (true)
{
IEnumerable<MongoDB.Bson.BsonDocument> page = null;
if(pageNo == 1)
page = mt.Find(_ => true).Limit(PAGE_SIZE).ToListAsync().Result;
else
page = mt.Find(_ => true).Skip(PAGE_SIZE * (pageNo -1)).Limit(PAGE_SIZE).ToListAsync().Result;
if(page.Count() == 0)
break;
foreach (var p in page)
{
ObjectId id = (ObjectId)p["_id"];
DeleteResult dr = mt.DeleteOneAsync(Builders<BsonDocument>.Filter.Eq("_id", id)).Result;
if (dr.IsAcknowledged)
{
if (dr.DeletedCount != 1)
{
throw new Exception(string.Format("Count [value:{0}] after delete is invalid", dr.DeletedCount));
}
}
else
throw new Exception(string.Format("Delete for [_id:{0}] was not acknowledged", id.ToString()));
}
count += page.Count();
}
Console.WriteLine("Done, count:{0}", count);
Console.ReadLine();
}
Upvotes: 0
Views: 1029
Reputation: 1959
The cursor is not isolated so it recognizes that you've deleted some data and when you pull the next page you are skipping records you intend to delete. If you pulled page 1 each time it would work like what it seems you want it to.
Upvotes: 2