【问题标题】:Deserializing from MongoDB Enumerable as ICollection<T>从 MongoDB Enumerable 反序列化为 ICollection<T>
【发布时间】:2013-03-24 19:42:23
【问题描述】:

我在 MongoDB 中反序列化 TwitterStatus 类时遇到以下问题,这是使用 MongoDB C# 驱动程序 1.8.0.124 和 TweetSharp 2.0 的失败单元测试:

using Microsoft.VisualStudio.TestTools.UnitTesting;
using MongoDB.Driver;
using MongoDB.Driver.Builders;
using System.Linq;
using TweetSharp;

namespace DS.Model.Tests
{
    [TestClass]
    public class TestMongoSerialization
    {
        [TestMethod]
        public void CanDeserializeTwitterEntitiesFromMongoDB()
        {
            var server = new MongoClient().GetServer();
            MongoDatabase db = server.GetDatabase("test");
            var tweets = db.GetCollection<TwitterStatus>("tweetSerialized");

            var tweet = Newtonsoft.Json.JsonConvert.DeserializeObject<TwitterStatus>(tweetWithTwitterEntityiesSerialized);
            Assert.AreEqual(1, tweet.Entities.Count());
            Assert.AreEqual(TwitterEntityType.Url, tweet.Entities.First().EntityType);
            tweets.Save(tweet);
            Assert.AreEqual(1, tweets.FindAll().Count()); 

            var tweetFromMango = tweets.FindOne(Query<TwitterStatus>.EQ(s => s.Id, 315278676398858240));
            Assert.AreEqual(TwitterEntityType.Url, tweetFromMango.Entities.First().EntityType); // throws exception [1]
        }

        string tweetWithTwitterEntityiesSerialized = @"{""Id"":315278676398858240,""Text"":""TeePublic Funds 22 Designs "",""RetweetedStatus"":null,""created_at"":""2013-03-23T01:47:48Z"",""geo"":null,""Entities"":{""user_mentions"":[],""hashtags"":[],""urls"":[{""url"":""http://t.co/rBGN46rua7"",""expanded_url"":""http://zite.to/10uCED9"",""indices"":[71,93],""EntityType"":2}],""media"":[]},""possibly_sensitive"":false,""Place"":null}";

    }
}

抛出的异常是Enumerable class TwitterEntities does not implement ICollection&lt;T&gt; so it can't be deserialized,下面是完整的堆栈跟踪。

完整的堆栈跟踪:

System.IO.FileFormatException: An error occurred while deserializing the Entities property of class TweetSharp.TwitterStatus: 
Enumerable class TwitterEntities does not implement ICollection<T> so it can't be deserialized. ---> MongoDB.Bson.BsonSerializationException: Enumerable class TwitterEntities does not implement ICollection<T> so it can't be deserialized.
Result StackTrace:  
at MongoDB.Bson.Serialization.Serializers.EnumerableSerializer`1.CreateInstance(Type type)
   at MongoDB.Bson.Serialization.Serializers.EnumerableSerializer`1.Deserialize(BsonReader bsonReader, Type nominalType, Type actualType, IBsonSerializationOptions options)
   at MongoDB.Bson.Serialization.BsonClassMapSerializer.DeserializeMemberValue(BsonReader bsonReader, BsonMemberMap memberMap)
 --- End of inner exception stack trace ---
    at MongoDB.Bson.Serialization.BsonClassMapSerializer.DeserializeMemberValue(BsonReader bsonReader, BsonMemberMap memberMap)
   at MongoDB.Bson.Serialization.BsonClassMapSerializer.Deserialize(BsonReader bsonReader, Type nominalType, Type actualType, IBsonSerializationOptions options)
   at MongoDB.Bson.Serialization.BsonClassMapSerializer.Deserialize(BsonReader bsonReader, Type nominalType, IBsonSerializationOptions options)
   at MongoDB.Bson.Serialization.BsonSerializer.Deserialize(BsonReader bsonReader, Type nominalType, IBsonSerializationOptions options)

如果没有此异常,我如何从 mongoDB 反序列化 TweetStatus 类? 供参考有the TwitterEntity classes

【问题讨论】:

    标签: c# mongodb serialization bson tweetsharp


    【解决方案1】:

    TwitterStatus 有一个属性

    public virtual TwitterEntities Entities
    

    它被定义为

    public class TwitterEntities : IEnumerable<TwitterEntity>
    

    现在,当反序列化 JSon.NET 时,会创建一个 TwitterEntities 实例,然后尝试用 TwitterEntity 项填充它。但要做到这一点,它需要一个 Add 方法,而 IEnumerable 没有提供。 但是ICollection(T) 确实提供了 Add 方法,这就是它要求 ICollection(T) 的原因。

    但如果您使用的是 MongoDb IMO,则不应直接进行任何 JSON 转换。您应该只有简单的 POCO 类,MongoDb 驱动程序会自动为您处理这些类实例的(反)序列化。

    这就是使用文档数据库的美妙之处。

    【讨论】:

    • 谢谢;我希望将 TwitterStatus 用作 MongoDB 的简单 POCO 类,但我想我需要将它映射到我自己的更简单的类。
    猜你喜欢
    • 2022-06-14
    • 1970-01-01
    • 2018-10-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-01-08
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多