如何为方法MongoDB.Bson.Serialization.BsonSerializer.Deserialize

时间:2019-02-02 04:08:07

标签: c# mongodb serialization

我使用MongoDB.Bson.Serialization.BsonSerializer.Deserialize()方法从MongoDB.Bson.BsonDocument反序列化为MyType。但是该方法始终符合System.FormatException,因为MyType中的字段与BsonDocument中的字段并非100%匹配。

我试图将一个复杂的json对象(称为mobj)从MongoDB(查询结果)转换为C#对象(称为csobj),以便可以处理数据。我使用的csobj中的默认数据类型是字符串。但是mobj太复杂了,我们知道它的架构更少。

一旦在mobj中遇到诸如BinData(0,“”),BinData(1,“”),BinData(2,“”),ISODate(“”)等数据类型,则可能会发生System.FormatException。

一旦mobj中有其他新字段,则可能会发生System.FormatException。

一旦字段名称中有空格,例如“第一页”:“ XXXX”,则可能会发生System.FormatException,并且直到现在我都不知道如何解决该问题。

var client = new MongoClient("mongodb://xxxxxx");
var database = client.GetDatabase("xxxxxxxxxx");
var collection = database.GetCollection<BsonDocument>("xxxxxxxxxx");

var results = await collection.Aggregate<BsonDocument>(filterBsonDocumentArray).ToListAsync();

foreach (var doc in results)
{
    var model = MongoDB.Bson.Serialization.BsonSerializer.Deserialize<MyType>(doc); // always meet exception here
}

异常示例:

(mongodb数据类型无法与字符串映射)

System.FormatException:反序列化MongoQueryDemo.MyType类的Id属性时发生错误:无法反序列化BsonType'Binary'中的'String'。 ---> System.FormatException:无法从BsonType“二进制”反序列化“字符串”。

(mongo中的_id在C#对象自动中找不到UserId)

System.FormatException:元素'_id'与MongoQueryDemo.MyType类的任何字段或属性都不匹配。

我的问题在这里列出:

  1. 有什么办法告诉反序列化器,请不要区分大小写;

  2. 有什么方法可以自定义从mobj到csobj的字段名映射,例如定义“ _id”-> UserId,“ Ip Addr”->“ IpAddr”;

  3. 是否可以自定义数据类型,让数据类型BinData(0,“”),BinData(1,“”),BinData(2,“”),ISODate(“”)都可以被转换成没有System.FormatException的字符串;

  4. 有没有办法处理整个复杂子对象到C#字符串的映射,而不管其字段如何?由于它的动态模式较少,因此mongodb较少,我无法在子对象中预定义任何未知字段。

2 个答案:

答案 0 :(得分:0)

该属性会将字段名称从 mobj 映射到 csojo `[BsonElement(@"52WeekChange")]

答案 1 :(得分:0)

您有几个选项,可以探索here, in the docs。 (以下示例来自那里。)

您可以使用 ClassMap

BsonClassMap.RegisterClassMap<MyClass>(cm => {
    cm.MapProperty(c => c.SomeProperty);
    cm.MapProperty(c => c.AnotherProperty);
});

如果您更喜欢在 c# 类型声明中定义映射,则可以使用属性。

BsonContructor 可用于在对象构造期间映射属性:

public class Person
{
  public string FirstName { get; set; }
  public string LastName { get; set; }

  // You can use this on one or more overloads as well:
  [BsonConstructor]
  public Person(string firstName, string lastName)
  {
    FirstName = firstName;
    LastName = lastName;
  }
}

BsonElement 是一个属性级的解决方案:

public class MyClass {
    // The first parameter ("sp") is an optional mongodb field name mapping.
    [BsonElement("sp")]
    public string SomeProperty { get; set; }
}