Overview
In this guide, you can learn how to perform multiple write operations in a single database call by using bulk write operations.
Consider a scenario in which you want to insert a document, update multiple other documents, then delete a document. If you use individual methods, each operation requires its own database call.
By using a bulk write operation, you can perform multiple write operations in fewer database calls. You can perform bulk write operations at the following levels:
Collection: You can use the
IMongoCollection.BulkWrite()orIMongoCollection.BulkWriteAsync()method to perform bulk write operations on a single collection. These methods make a database call for each type of write operation. For example, the methods perform multiple update operations in one call, but make two separate calls to the database for an insert operation and a replace operation.Client: If your application connects to MongoDB Server version 8.0 or later, you can use the
IMongoClient.BulkWrite()orIMongoClient.BulkWriteAsync()method to perform bulk write operations on multiple collections and databases in the same cluster. This method performs all write operations in one database call.
Sample Data
The examples in this guide use the sample_restaurants.restaurants and sample_mflix.movies collections from the Atlas sample
datasets. To learn how to create a free MongoDB Atlas cluster and load the sample datasets, see the MongoDB Get Started guide.
Tip
Bulk Write Operations with POCOs
The examples in this guide use the BsonDocument type for the TDocument type in all generic classes. You can also use a Plain Old CLR Object (POCO) for these classes. To do so, you must define a class that represents the documents in your collection. The class must have properties that match the fields in your documents. For more information, see POCOs.
Collection Bulk Write
Bulk write operations contain one or more write operations. For each write operation you want to perform, create an instance of one of the following WriteModel<TDocument> classes:
DeleteManyModel<TDocument>DeleteOneModel<TDocument>InsertOneModel<TDocument>ReplaceOneModel<TDocument>UpdateManyModel<TDocument>UpdateOneModel<TDocument>
The following sections show how to create and use instances of the preceding classes to perform the corresponding write operation in a bulk write operation. The Perform the Bulk Operation section demonstrates how to pass a list of models to the BulkWrite() or BulkWriteAsync() method to perform the bulk operation.
Insert Operations
To perform an insert operation, create an InsertOneModel<TDocument> instance and specify the document you want to insert.
The following example creates an instance of the InsertOneModel<BsonDocument> class. This instance directs the driver to insert a document in which the "name" field is "Mongo's Deli" into the restaurants collection.
var insertOneModel = new InsertOneModel<BsonDocument>( new BsonDocument{ { "name", "Mongo's Deli" }, { "cuisine", "Sandwiches" }, { "borough", "Manhattan" }, { "restaurant_id", "1234" } } );
To insert multiple documents, create an instance of InsertOneModel<TDocument> for each document.
Important
Duplicate Key Error
When performing a bulk operation, the InsertOneModel<TDocument> cannot insert a document with an _id that already exists in the collection. In this situation, the driver throws a MongoBulkWriteException.
Update Operations
To update a single document, create an instance of UpdateOneModel<TDocument> and pass the following arguments:
Query filter that specifies the criteria used to match documents in your collection. To learn more about specifying a query, see Query and Projection Operators in the MongoDB Server manual.
Update document that describes the update to perform. To learn more about specifying an update, see Update Operators in the MongoDB Server manual.
An UpdateOneModel<TDocument> instance specifies an update for the first document that matches your query filter.
In the following code example, the UpdateOneModel<BsonDocument> object represents an update operation on the restaurants collection. The operation matches the first document in the collection where the value of the name field is "Mongo's Deli". It then updates the value of the cuisine field in the matched document to "Sandwiches and Salads".
var updateOneModel = new UpdateOneModel<BsonDocument>( Builders<BsonDocument>.Filter.Eq("name", "Mongo's Deli"), Builders<BsonDocument>.Update.Set("cuisine", "Sandwiches and Salads") );
To update multiple documents, create an instance of UpdateManyModel<TDocument> and pass the same arguments as for UpdateOneModel<TDocument>. The UpdateManyModel<TDocument> class specifies updates for all documents that match your query filter.
In the following code example, the UpdateManyModel<BsonDocument> object represents an update operation on the restaurants collection. The operation matches all documents in the collection where the value of the name field is "Mongo's Deli". It then updates the value of the cuisine field to "Sandwiches and Salads".
var updateManyModel = new UpdateManyModel<BsonDocument>( Builders<BsonDocument>.Filter.Eq("name", "Mongo's Deli"), Builders<BsonDocument>.Update.Set("cuisine", "Sandwiches and Salads") );
Replace Operations
A replace operation removes all fields and values of a specified document and replaces them with new fields and values that you specify. To perform a replace operation, create an instance of ReplaceOneModel<TDocument> and pass a query filter and the fields and values you want to replace the matching document with.
In the following example, the ReplaceOneModel<BsonDocument> object represents a replace operation on the restaurants collection. The operation matches the document in the collection where the value of the restaurant_id field is "1234". It then removes all fields other than _id from this document, and sets new values in the name, cuisine, borough, and restaurant_id fields.
var replaceOneModel = new ReplaceOneModel<BsonDocument>( Builders<BsonDocument>.Filter.Eq("restaurant_id", "1234"), new BsonDocument{ { "name", "Mongo's Pizza" }, { "cuisine", "Pizza" }, { "borough", "Brooklyn" }, { "restaurant_id", "5678" } } );
To replace multiple documents, you must create an instance of ReplaceOneModel<TDocument> for each document.
Delete Operations
To delete a document, create an instance of DeleteOneModel<TDocument> and pass a query filter specifying the document you want to delete. A DeleteOneModel<TDocument> instance provides instructions to delete only the first document that matches your query filter.
In the following code example, the DeleteOneModel<BsonDocument> object represents a delete operation on the restaurants collection. The operation matches and deletes the first document where the value of the restaurant_id field is "5678".
var deleteOneModel = new DeleteOneModel<BsonDocument>( Builders<BsonDocument>.Filter.Eq("restaurant_id", "5678") );
To delete multiple documents, create an instance of DeleteManyModel<TDocument> and pass a query filter specifying the documents you want to delete. An instance of DeleteManyModel<TDocument> provides instructions to remove all documents that match your query filter.
In the following code example, the DeleteManyModel<BsonDocument> object represents a delete operation on the restaurants collection. The operation matches and deletes all documents where the value of the name field is "Mongo's Deli".
var deleteManyModel = new DeleteManyModel<BsonDocument>( Builders<BsonDocument>.Filter.Eq("name", "Mongo's Deli") );
Perform the Bulk Operation
After you define a WriteModel instance for each operation that you want to perform, create an instance of a class that implements the IEnumerable interface. Add your WriteModel objects to this IEnumerable, then pass the IEnumerable to the BulkWrite() or BulkWriteAsync() method. By default, these methods run the operations in the order they're defined in the list.
Tip
IEnumerable
Array and List are two common classes that implement the IEnumerable interface.
Select from the following tabs to view how to use the synchronous BulkWrite() method and the asynchronous BulkWriteAsync() method to perform a bulk write operation on the restaurants collection:
var models = new List<WriteModel<BsonDocument>> { new InsertOneModel<BsonDocument>( new BsonDocument{ { "name", "Mongo's Deli" }, { "cuisine", "Sandwiches" }, { "borough", "Manhattan" }, { "restaurant_id", "1234" } } ), new InsertOneModel<BsonDocument>( new BsonDocument{ { "name", "Mongo's Deli" }, { "cuisine", "Sandwiches" }, { "borough", "Brooklyn" }, { "restaurant_id", "5678" } } ), new UpdateManyModel<BsonDocument>( Builders<BsonDocument>.Filter.Eq("name", "Mongo's Deli"), Builders<BsonDocument>.Update.Set("cuisine", "Sandwiches and Salads") ), new DeleteOneModel<BsonDocument>( Builders<BsonDocument>.Filter.Eq("restaurant_id", "1234") ) }; var results = collection.BulkWrite(models); Console.WriteLine(results);
var models = new List<WriteModel<BsonDocument>> { new InsertOneModel<BsonDocument>( new BsonDocument{ { "name", "Mongo's Deli" }, { "cuisine", "Sandwiches" }, { "borough", "Manhattan" }, { "restaurant_id", "1234" } } ), new InsertOneModel<BsonDocument>( new BsonDocument{ { "name", "Mongo's Deli" }, { "cuisine", "Sandwiches" }, { "borough", "Brooklyn" }, { "restaurant_id", "5678" } } ), new UpdateManyModel<BsonDocument>( Builders<BsonDocument>.Filter.Eq("name", "Mongo's Deli"), Builders<BsonDocument>.Update.Set("cuisine", "Sandwiches and Salads") ), new DeleteOneModel<BsonDocument>( Builders<BsonDocument>.Filter.Eq("restaurant_id", "1234") ) }; var results = await collection.BulkWriteAsync(models); Console.WriteLine(results);
The preceding code examples produce the following output:
MongoDB.Driver.BulkWriteResult1+Acknowledged[MongoDB.Bson.BsonDocument]
Note
When the driver runs a bulk operation, it uses the write concern of the target collection. The driver reports all write concern errors after attempting all operations, regardless of execution order.
Customize Bulk Write Operation
When you call the BulkWrite() or BulkWriteAsync() method, you can pass an instance of the BulkWriteOptions class. The BulkWriteOptions class contains the following properties, which represent options you can use to configure the bulk write operation:
Property | Description |
|---|---|
| Specifies whether the operation bypasses document-level validation. For more
information, see Schema
Validation in the MongoDB Server
manual. |
| A comment to attach to the operation, in the form of a |
| If |
| A map of parameter names and values, in the form of a |
The following code examples use a BulkWriteOptions object to perform an unordered bulk write operation:
Return Value
The BulkWrite() and BulkWriteAsync() methods return a BulkWriteResult object that contains the following properties:
Property | Description |
|---|---|
| Indicates whether the server acknowledged the bulk write operation. If the
value of this property is |
| The number of documents deleted, if any. |
| The number of documents inserted, if any. |
| The number of documents matched for an update, if applicable. |
| The number of documents modified, if any. |
| Indicates whether the modified count is available. |
| A list that contains information about each request that resulted in an upsert operation. |
| The number of requests in the bulk operation. |
Handling Exceptions
If any of the operations in a bulk write operation fail, the .NET/C# Driver throws a BulkWriteError and does not perform any further operations.
A BulkWriteError object contains the Index property that describes the index of the request that resulted in an error.
Client Bulk Write
When connecting to a deployment running MongoDB Server 8.0 or later, you can use the IMongoClient.BulkWrite() or IMongoClient.BulkWriteAsync() method to write to multiple databases and collections in the same cluster. These methods perform all write operations in a single call.
For each write operation you want to perform, create an instance of one of the following BulkWriteModel classes:
BulkWriteInsertOneModel<TDocument>BulkWriteUpdateOneModel<TDocument>BulkWriteUpdateManyModel<TDocument>BulkWriteReplaceOneModel<TDocument>BulkWriteDeleteOneModel<TDocument>BulkWriteDeleteManyModel<TDocument>
The following sections show how to create and use instances of the preceding classes to perform the corresponding write operation in a bulk write. The Perform the Bulk Operation section demonstrates how to pass a list of models to the BulkWrite() or BulkWriteAsync() method to perform the bulk operation.
Insert Operations
To perform an insert operation, create an instance of the BulkWriteInsertOneModel<TDocument> class. The BulkWriteInsertOneModel<TDocument> constructor accepts the following parameters:
Parameter | Description |
|---|---|
| The database and collection to insert the BSON document into. |
| The document to insert into the collection. |
The following example creates instances of the BulkWriteInsertOneModel<TDocument> class. These instances direct the driver to insert documents into the sample_restaurants.restaurants and sample_mflix.movies collections.
var restaurantToInsert = new BulkWriteInsertOneModel<BsonDocument>( "sample_restaurants.restaurants", new BsonDocument{ { "name", "Mongo's Deli" }, { "cuisine", "Sandwiches" }, { "borough", "Manhattan" }, { "restaurant_id", "1234" } } ); var movieToInsert = new BulkWriteInsertOneModel<BsonDocument>( "sample_mflix.movies", new BsonDocument{ { "title", "Silly Days" }, { "year", 2022 } } );
Update Operations
To update a single document, create an instance of the BulkWriteUpdateOneModel<TDocument> class. The BulkWriteUpdateOneModel<TDocument> constructor accepts the following parameters:
Parameter | Description |
|---|---|
| The database and collection to insert the BSON document into. |
| The query filter that specifies the criteria used to match documents in your collection.
The |
| The update operation you want to perform. For more information about update
operations, see Field Update Operators
in the MongoDB Server manual. |
| |
| Optional. The index to use to scan for documents.
See the MongoDB Server manual
for more information. |
| Optional. Specifies whether the update operation performs an upsert operation if no
documents match the query filter. See the MongoDB Server manual
for more information. |
| Specifies which array elements to modify for an update operation on an array field.
See the MongoDB Server manual
for more information. |
In the following code example, the BulkWriteUpdateOneModel<BsonDocument> objects represent update operations on the sample_restaurants.restaurants and sample_mflix.movies collections.
var restaurantUpdate = new BulkWriteUpdateOneModel<BsonDocument>( "sample_restaurants.restaurants", Builders<BsonDocument>.Filter.Eq("name", "Mongo's Deli"), Builders<BsonDocument>.Update.Set("cuisine", "Sandwiches and Salads") ); var movieUpdate = new BulkWriteUpdateOneModel<BsonDocument>( "sample_mflix.movies", Builders<BsonDocument>.Filter.Eq("title", "Carrie"), Builders<BsonDocument>.Update.Set("seen", True) );
To update multiple documents, create an instance of the BulkWriteUpdateManyModel<TDocument> class. The constructor for this class accepts the same parameters as the BulkWriteUpdateOneModel<TDocument> constructor. The BulkWriteUpdateManyModel<TDocument> operation updates all documents that match your query filter.
In the following code example, the BulkWriteUpdateManyModel<BsonDocument> object represents an update operation on the sample_restaurants.restaurants collection. The operation matches all documents in the collection where the value of the name field is "Starbucks". It then updates the value of the cuisine field to "Coffee (Chain)".
var updateManyModel = new BulkWriteUpdateManyModel<BsonDocument>( "sample_restaurants.restaurants", Builders<BsonDocument>.Filter.Eq("name", "Starbucks"), Builders<BsonDocument>.Update.Set("cuisine", "Coffee (Chain)") );
Replace Operations
To replace the fields in a document, create an instance of the BulkWriteReplaceOneModel<TDocument> class. The BulkWriteReplaceOneModel<TDocument> constructor accepts the following parameters:
Parameter | Description |
|---|---|
| The database and collection to insert the BSON document into. |
| The query filter that specifies the criteria used to match documents in your collection.
The |
| The replacement document, which specifies the fields and values to insert in the
target document. |
| |
| Optional. The index to use to scan for documents.
See the MongoDB Server manual
for more information. |
| Optional. Specifies whether the update operation performs an upsert operation if no
documents match the query filter.
See the MongoDB Server manual
for more information. |
In the following example, the BulkWriteReplaceOneModel<BsonDocument> objects represent replace operations on the sample_restaurants.restaurants and sample_mflix.movies collections.
var restaurantReplacement = new BulkWriteReplaceOneModel<BsonDocument>( "sample_restaurants.restaurants", Builders<BsonDocument>.Filter.Eq("restaurant_id", "1234"), new BsonDocument{ { "name", "Mongo's Pizza" }, { "cuisine", "Pizza" }, { "borough", "Brooklyn" }, { "restaurant_id", "5678" } } ); var movieReplacement = new BulkWriteReplaceOneModel<BsonDocument>( "sample_mflix.movies", Builders<BsonDocument>.Filter.Eq("title", "Insomnia"), new BsonDocument{ { "name", "Loving Sylvie" }, { "year", 1999 } } );
Delete Operations
To delete a document, create an instance of the BulkWriteDeleteOneModel<TDocument> class. The BulkWriteDeleteOneModel<TDocument> constructor accepts the following parameters:
Parameter | Description |
|---|---|
| The database and collection to insert the BSON document into. |
| The query filter that specifies the criteria used to match documents in your collection.
The |
| |
| Optional. The index to use to scan for documents.
See the MongoDB Server manual
for more information. |
In the following code example, the BulkWriteDeleteOneModel<BsonDocument> objects represent delete operations on the sample_restaurants.restaurants and sample_mflix.movies collections.
var restaurantToDelete = new BulkWriteDeleteOneModel<BsonDocument>( "sample_restaurants.restaurants", Builders<BsonDocument>.Filter.Eq("restaurant_id", "5678") ); var movieToDelete = new BulkWriteDeleteOneModel<BsonDocument>( "sample_mflix.movies", Builders<BsonDocument>.Filter.Eq("title", "Mr. Nobody") );
To delete multiple documents, create an instance of the BulkWriteDeleteManyModel<TDocument> class and pass a query filter that specifies the document that you want to delete. The DeleteMany operation removes all documents that match your query filter.
In the following code example, the BulkWriteDeleteManyModel<BsonDocument> object represents a delete operation on the sample_restaurants.restaurants collection. The operation matches and deletes all documents where the value of the name field is "Mongo's Deli".
var deleteManyModel = new BulkWriteDeleteManyModel<BsonDocument>( "sample_restaurants.restaurants", Builders<BsonDocument>.Filter.Eq("name", "Mongo's Deli") );
Perform the Bulk Operation
After you define a BulkWriteModel instance for each operation that you want to perform, create an instance of a class that implements the IReadOnlyList interface. Add your BulkWriteModel objects to this IReadOnlyList, then pass the IReadOnlyList to the BulkWrite() or BulkWriteAsync() method. By default, these methods run the operations in the order they're defined in the collection.
Tip
IReadOnlyList
Array and List are two common classes that implement the IReadOnlyList interface.
Select from the following tabs to view how to use the synchronous BulkWrite() method and the asynchronous BulkWriteAsync() method to perform a bulk write operation on multiple namespaces.
var client = new MongoClient("mongodb://localhost:27017"); var restaurantNamespace = "sample_restaurants.restaurants"; var movieNamespace = "sample_mflix.movies"; var bulkWriteModels = new[] { new BulkWriteInsertOneModel<BsonDocument>( restaurantNamespace, new BsonDocument{ { "name", "Mongo's Deli" }, { "cuisine", "Sandwiches" }, { "borough", "Manhattan" }, { "restaurant_id", "1234" } } ), new BulkWriteInsertOneModel<BsonDocument>( movieNamespace, new BsonDocument{ { "name", "Sarah's Secret" }, { "year", 1988 } } ), new BulkWriteUpdateManyModel<BsonDocument>( restaurantNamespace, Builders<BsonDocument>.Filter.Eq("name", "Mongo's Deli"), Builders<BsonDocument>.Update.Set("cuisine", "Sandwiches and Salads") ), new BulkWriteDeleteOneModel<BsonDocument>( movieNamespace, Builders<BsonDocument>.Filter.Eq("title", "House") ) }; var result = client.BulkWrite(bulkWriteModels); Console.WriteLine(result);
var client = new MongoClient("mongodb://localhost:27017"); var restaurantNamespace = "sample_restaurants.restaurants"; var movieNamespace = "sample_mflix.movies"; var bulkWriteModels = new[] { new BulkWriteInsertOneModel<BsonDocument>( restaurantNamespace, new BsonDocument{ { "name", "Mongo's Deli" }, { "cuisine", "Sandwiches" }, { "borough", "Manhattan" }, { "restaurant_id", "1234" } } ), new BulkWriteInsertOneModel<BsonDocument>( movieNamespace, new BsonDocument{ { "name", "Sarah's Secret" }, { "year", 1988 } } ), new BulkWriteUpdateManyModel<BsonDocument>( restaurantNamespace, Builders<BsonDocument>.Filter.Eq("name", "Mongo's Deli"), Builders<BsonDocument>.Update.Set("cuisine", "Sandwiches and Salads") ), new BulkWriteDeleteOneModel<BsonDocument>( movieNamespace, Builders<BsonDocument>.Filter.Eq("title", "House") ) }; var result = await client.BulkWriteAsync(bulkWriteModels); Console.WriteLine(result);
The preceding code examples produce the following output:
BulkWriteResult({'writeErrors': [], 'writeConcernErrors': [], 'nInserted': 2, 'nUpserted': 0, 'nMatched': 2, 'nModified': 2, 'nRemoved': 1, 'upserted': []}, acknowledged=True)
Customize Bulk Write
When you call the BulkWrite() or BulkWriteAsync() method, you can pass an instance of the ClientBulkWriteOptions class. The ClientBulkWriteOptions class contains the following properties, which represent options you can use to configure the bulk write operation:
Property | Description |
|---|---|
| Specifies whether the operation bypasses document-level validation. For more
information, see Schema
Validation in the MongoDB Server
manual. |
| A comment to attach to the operation, in the form of a |
| If |
| A map of parameter names and values, in the form of a |
| Specifies whether the |
| The write concern to use for the write operation, as a value from the |
The following code examples use a ClientBulkWriteOptions object to customize the bulk write operation:
Return Value
The BulkWrite() and BulkWriteAsync() methods return a ClientBulkWriteResult object that contains the following properties:
Property | Description |
|---|---|
| Indicates whether the server acknowledged the bulk write operation. If the
value of this property is |
| An |
| The number of documents deleted, if any. |
| An |
| The number of documents inserted, if any. |
| The number of documents matched for an update, if applicable. |
| The number of documents modified, if any. |
| An |
| The number of documents upserted, if any. |
Handling Exceptions
If any of the operations in a bulk write operation fail, the .NET/C# Driver throws a ClientBulkWriteException and does not perform any further operations.
A ClientBulkWriteException object contains the following properties:
Property | Description |
|---|---|
| The connection identifier. |
| The error message. |
| A dictionary of errors that occurred during the bulk write operation. |
| The results of any successful operations performed before the exception was thrown. |
| Write concern errors that occurred during execution of the bulk write operation. |
| The inner exception. |
Collation
To configure collation for your operation, create an instance of the Collation class.
The following table describes the parameters that the Collation constructor accepts. It also lists the corresponding class property that you can use to read each setting's value.
Parameter | Description | Class Property |
|---|---|---|
| Specifies the International Components for Unicode (ICU) locale. For a list of
supported locales,
see Collation Locales and Default Parameters
in the MongoDB Server Manual. |
|
| (Optional) Specifies whether to include case comparison. |
|
| (Optional) Specifies the sort order of case differences during tertiary level comparisons. |
|
| (Optional) Specifies the level of comparison to perform, as defined in the
ICU documentation. |
|
| (Optional) Specifies whether the driver compares numeric strings as numbers. |
|
| (Optional) Specifies whether the driver considers whitespace and punctuation as base
characters for purposes of comparison. |
|
| (Optional) Specifies which characters the driver considers ignorable when
the |
|
| (Optional) Specifies whether the driver normalizes text as needed. |
|
| (Optional) Specifies whether strings containing diacritics sort from the back of the string
to the front. |
|
For more information about collation, see the Collation page in the MongoDB Server manual.
Additional Information
To learn how to perform individual write operations, see the following guides:
API Documentation
To learn more about any of the methods or types discussed in this guide, see the following API documentation:
Client Bulk Write