Overview
In this guide, you can learn how to customize the way the MongoDB .NET/C# Driver maps BSON documents to and from C# classes. Read this page to learn more about the default class mapping behavior, or if you must customize the way the driver serializes or deserializes your data.
You can also use POCO attributes to set serialization behavior. To learn more, see the POCOs guide.
Automatic Class Mapping
When you use a class, rather than a BsonDocument
, to represent data in a MongoDB collection, the .NET/C# Driver automatically creates a class map that it uses to serialize or deserialize your data. It does this mapping by matching the name of the field in the document to the name of the property in the class.
Important
Match the type of the property in your class to the type of the field in the document. The .NET/C# Driver instantiates a serializer based on the type of the property in your class. If the types don't match when the driver attempts to deserialize the data, the serializer throws an exception.
Manually Creating A Class Map
You can bypass the driver's automatic class mapping functionality, and manually define the class map by using the RegisterClassMap()
method.
The following example defines a Person
class:
public class Person { public string Name { get; set; } public int Age { get; set; } public List<string> Hobbies {get; set;} }
The following code demonstrates how to register the class map for the Person
class:
BsonClassMap.RegisterClassMap<Person>(classMap => { classMap.MapMember(p => p.Name); classMap.MapMember(p => p.Age); classMap.MapMember(p => p.Hobbies); });
Important
When to Register a Class Map
You must register a class map before it's needed in your code. We recommend registering class maps before initializing a connection with MongoDB.
You can also manually map a subset of class properties, while still allowing the driver to automatically map the remaining properties. To do this, register a class map and call the AutoMap()
method before manually specifying your properties.
In the following code example, the AutoMap()
method maps all properties of the Person
class, then manually adjusts the mapping for the Hobbies
field:
BsonClassMap.RegisterClassMap<Person>(classMap => { classMap.AutoMap(); classMap.MapMember(p => p.Hobbies).SetElementName("favorite_hobbies"); });
Customize Class Serialization
You can customize how the driver serializes and deserializes documents at the class level by applying attributes to the class or by calling methods while registering a class map.
Omit Fields
You can prevent specified fields from being serialized by using the UnmapMember()
method when registering a class map.
The following example shows how to create a class map to prevent the Age
property from being serialized:
BsonClassMap.RegisterClassMap<Person>(classMap => { classMap.AutoMap(); classMap.UnmapMember(p => p.Age); });
Tip
To learn about how to set this behavior by using a field attribute, see the Omit Fields section of the POCOs guide.
Ignore Extra Elements
When a BSON document is deserialized to a C# class, the .NET/C# Driver looks at the name of each field in the document and tries to find a matching property name in the class. By default, if a field in the document doesn't have a match in the class, the driver throws an exception.
You can choose to ignore any elements that do not have a matching class property by using the BsonIgnoreExtraElements
attribute. This prevents the driver from throwing an exception, and maps any other fields that have matching class properties.
The following example shows how to add a BsonIgnoreExtraElements
attribute to a class.
[ ]public class Person { public string Name { get; set; } public int Age { get; set; } public List<string> Hobbies {get; set;} }
You can also ignore any extra elements when registering a class map:
BsonClassMap.RegisterClassMap<Person>(classMap => { classMap.AutoMap(); classMap.SetIgnoreExtraElements(true); });
Identify Id Field
By default, the driver maps any public property named Id
, id
, or _id
to the BSON _id
field. To explicitly select the property to map to the _id
field, use the MapIdMember()
class map method.
The following code sample maps the Identifier
property to the _id
field:
BsonClassMap.RegisterClassMap<Person>(classMap => { classMap.AutoMap(); classMap.MapIdMember(p => p.Identifier); });
String IDs
If you are using strings to represent your documement IDs, you can use the IdMemberMap.SetSerializer()
class map method to serialize these values to ObjectId
instances in MongoDB. This way, you can customize how your ID values are represented in your application while adhering to MongoDB best practices for ID management in the database.
The following example directs the driver to serialize string ID values as ObjectId
values:
BsonClassMap.RegisterClassMap<Person>(classMap => { classMap.AutoMap(); classMap.IdMemberMap.SetSerializer(new StringSerializer(BsonType.ObjectId)); });
If you want the driver to generate valid 24-digit hex strings to use as your ID values, you can chain the SetIdGenerator()
method to the MapIdMember()
method and pass an instance of StringObjectIdGenerator
:
BsonClassMap.RegisterClassMap<Person>(classMap => { classMap.AutoMap(); classMap.MapIdMember(p => p.Identifier).SetIdGenerator(StringObjectIdGenerator.Instance); });
To learn more about ID generators, see the Specify an ID Generator section of the POCOs guide.
GUID IDs
If your application uses GUIDs as unique identifiers in your documents, you can register a class map to specify how Guid
values are serialized. By default, the driver uses the GuidGenerator
type to generate a unique value for the ID property. You must specify the GUID representation by initializing a GuidSerializer
.
The following code specifies the Standard
GUID representation when registering the class map:
BsonClassMap.RegisterClassMap<Person>(classMap => { classMap.AutoMap(); classMap.IdMemberMap.SetSerializer(new GuidSerializer(GuidRepresentation.Standard)); });
To learn more about serializing GUIDs, see the GUIDs guide.
Mapping with Constructors
By default, the .NET/C# Driver can automatically map a class only if the class has a constructor with no arguments. If you want the driver to use a constructor that accepts one or more arguments, you can add the BsonConstructor
attribute to the constructor. In this case, the driver examines the types to determine how to map the constructor arguments to class properties or fields.
When the driver creates a class map for the following Person
class, it will use the constructor marked with the BsonConstructor
attribute. The name
argument will map to the Name
property and the age
argument will map to the Age
property.
public class Person { public string Name { get; set; } public int Age { get; set; } public List<string> Hobbies {get; set;} [ ] public Person(string name, string age) { Name = name; Age = age; } }
Tip
Multiple BsonConstructor attributes
If there is more than one constructor with the BsonConstructor
attribute, the driver uses the constructor that has the most parameters with matching fields in the document.
You can also specify the constructor to use when registering your class map:
public class Person { public string Name { get; set; } public int Age { get; set; } public List<string> Hobbies {get; set;} public Person(string name, string age) { Name = name; Age = age; } } BsonClassMap.RegisterClassMap<Person>(classMap => { classMap.AutoMap(); classMap.MapCreator(p => new Person(p.Name, p.Age)); });
Customize Property Serialization
You can customize how the driver serializes a class property by adding attributes to the property. For more information about custom property serialization, see Custom Serialization.
Support Extra Elements
You can design your C# class to store any extra elements in your document that don't have matching class properties. To do this your class must have a BsonDocument
type property to hold the extra elements.
The following code uses the BsonExtraElements
attribute with the ExtraElements
property to direct the driver to store extra elements:
public class Person { public string Name { get; set; public int Age { get; set; } public List<string> Hobbies {get; set;} [ ] public BsonDocument ExtraElements {get; set;} }
You can also support extra elements when initializing a class map as follows:
BsonClassMap.RegisterClassMap<Person>(classMap => { classMap.AutoMap(); classMap.MapExtraElementsMember(p => p.ExtraElements); });
Note
After the driver serializes a class with extra elements back to BSON, the extra elements may not be in the same order as they were in the original document.
Dynamically Serialize Properties
You can use a method to determine whether to serialize a property. For the driver to automatically use the method when serializing, you must prefix the method name with ShouldSerialize
followed by the name of the property that the method applies to. When the driver sees a method with this naming convention, it uses that method to determine whether to serialize properties that have the provided property name.
The following example creates a method that only serializes the Age
property if its value is not equal to 0
. The driver does not serialize any properties whose values don't meet this requirement:
public class Person { public string Name { get; set; } public int Age { get; set; } public List<string> Hobbies {get; set;} public bool ShouldSerializeAge() { return Age != 0; } }
You can also specify the method while registering a class map:
BsonClassMap.RegisterClassMap<Employee>(classMap => { classMap.AutoMap(); classMap.MapMember(p => c.Age).SetShouldSerializeMethod( obj => ((Person) obj).Age != 0 ); });
Additional Information
For more information on using C# classes, see POCOs.