Introduction to MongoDb with .NET part 21: bulk writes in the MongoDb driver

Introduction

In the previous post we discussed how to delete documents with the MongoDb .NET driver. After all we’ve learnt about filter definitions and various options it was really easy to go through the various deletion-related functions.

We’ve covered all the CRUD operations in .NET. I’d like to show one more database manipulation option related to CRUD before we move on: bulk writes.

Bulk writing

Bulk writing is an operation where we send multiple insert, update or delete commands to the database at the same time. It’s important to keep in mind the individual commands in the bulk write are not executed one after the other in a sequential manner but are rather sent to the database in parallel to be executed. We’ve actually used bulk writing already but we didn’t know about it. The insert, update and delete operations all use bulk writes under the hood.

We can also issue our own bulk writes against the database where we can mix various insert, update and delete operations. The operations are contained withing specialised Model objects such as InsertOneModel, DeleteManyModel, UpdateOneModel etc.

The following example will insert two new restaurants, update an existing one and also delete another existing one. It also demonstrates the usage of BulkWriteOptions which allows us to defined whether the various models are executed in order or not:

ModelContext modelContext = ModelContext.Create(new ConfigFileConfigurationRepository(), new AppConfigConnectionStringRepository());
RestaurantDb newThaiRestaurant = new RestaurantDb();
newThaiRestaurant.Address = new RestaurantAddressDb()
{
	BuildingNr = "150",
	Coordinates = new double[] { 22.82, 99.12 },
	Street = "Old Street",
	ZipCode = 876654
};
newThaiRestaurant.Borough = "Somewhere in Thailand";
newThaiRestaurant.Cuisine = "Thai";
newThaiRestaurant.Grades = new List<RestaurantGradeDb>()
{
	new RestaurantGradeDb() {Grade = "A", InsertedUtc = DateTime.UtcNow, Score = "7" },
	new RestaurantGradeDb() {Grade = "B", InsertedUtc = DateTime.UtcNow, Score = "4" },
	new RestaurantGradeDb() {Grade = "B", InsertedUtc = DateTime.UtcNow, Score = "10" },
	new RestaurantGradeDb() {Grade = "B", InsertedUtc = DateTime.UtcNow, Score = "4" }
};
newThaiRestaurant.Id = 463456435;
newThaiRestaurant.Name = "FavThai";

RestaurantDb newThaiRestaurantTwo = new RestaurantDb();
newThaiRestaurantTwo.Address = new RestaurantAddressDb()
{
	BuildingNr = "13",
	Coordinates = new double[] { 22.82, 99.12 },
	Street = "Wide Street",
	ZipCode = 345456
};
newThaiRestaurantTwo.Borough = "Somewhere in Thailand";
newThaiRestaurantTwo.Cuisine = "Thai";
newThaiRestaurantTwo.Grades = new List<RestaurantGradeDb>()
{				
	new RestaurantGradeDb() {Grade = "A", InsertedUtc = DateTime.UtcNow, Score = "4" },
	new RestaurantGradeDb() {Grade = "B", InsertedUtc = DateTime.UtcNow, Score = "10" },
	new RestaurantGradeDb() {Grade = "C", InsertedUtc = DateTime.UtcNow, Score = "4" }
};
newThaiRestaurantTwo.Id = 463456436;
newThaiRestaurantTwo.Name = "ThaiDinner";

var updateDefinitionBorough = Builders<RestaurantDb>.Update.Set(r => r.Borough, "The middle of Thailand");

FilterDefinition<RestaurantDb> deletionFilterDefinition = Builders<RestaurantDb>.Filter.Eq(r => r.Name, "PakistaniKing");

BulkWriteResult bulkWriteResult = modelContext.Restaurants.BulkWrite(new WriteModel<RestaurantDb>[]
{
	new InsertOneModel<RestaurantDb>(newThaiRestaurant),
	new InsertOneModel<RestaurantDb>(newThaiRestaurantTwo),
	new UpdateOneModel<RestaurantDb>(Builders<RestaurantDb>.Filter.Eq(r => r.Name, "RandomThai"), updateDefinitionBorough),
	new DeleteOneModel<RestaurantDb>(deletionFilterDefinition)
}, new BulkWriteOptions() { IsOrdered = false });

Debug.WriteLine(string.Concat("Deleted count: ", bulkWriteResult.DeletedCount));
Debug.WriteLine(string.Concat("Inserted count: ", bulkWriteResult.InsertedCount));
Debug.WriteLine(string.Concat("Acknowledged: ", bulkWriteResult.IsAcknowledged));
Debug.WriteLine(string.Concat("Matched count: ", bulkWriteResult.MatchedCount));
Debug.WriteLine(string.Concat("Modified count: ", bulkWriteResult.ModifiedCount));
Debug.WriteLine(string.Concat("Request count: ", bulkWriteResult.RequestCount));
Debug.WriteLine(string.Concat("Upsert count: ", bulkWriteResult.Upserts));

The BulkWriteResult is sort of a mixture of UpdateResult and DeleteResult with some additional properties. The above code outputs the following results:

Deleted count: 1
Inserted count: 2
Acknowledged: true
Matched count: 1
Modified count: 1
Request count: 4
Upsert count: 0

We’ve now covered the classic CRUD cases in both the Mongo shell and the MongoDb .NET driver. It’s time to move on to an entirely different beast of queries: aggregations.

You can view all posts related to data storage on this blog here.

Advertisement

About Andras Nemes
I'm a .NET/Java developer living and working in Stockholm, Sweden.

One Response to Introduction to MongoDb with .NET part 21: bulk writes in the MongoDb driver

  1. Adrian says:

    Thanks for authoring this helpful blog series. I have the following question.

    These two sentences seem to conflict with each other:
    1) “It’s important to keep in mind the individual commands in the bulk write are not executed one after the other in a sequential manner but are rather sent to the database in parallel to be executed.”
    2) “It also demonstrates the usage of BulkWriteOptions which allows us to defined whether the various models are executed in order or not:”

    So which is it? Can the order be predetermined or not?

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

Elliot Balynn's Blog

A directory of wonderful thoughts

Software Engineering

Web development

Disparate Opinions

Various tidbits

chsakell's Blog

WEB APPLICATION DEVELOPMENT TUTORIALS WITH OPEN-SOURCE PROJECTS

Once Upon a Camayoc

Bite-size insight on Cyber Security for the not too technical.

%d bloggers like this: