RavenDB:反序列化嵌套数组

时间:2015-03-09 20:08:19

标签: ravendb nosql

假设我将以下类序列化并存储为RavenDB的文档:

public class Block
{
    public string Id { get; set; }
    public List<List<dynamic>> data { get; set; }
}

存储后,可以在数据库中看到这样的文档:

{
"Id": "f539770a",
"columns": [ 
              [ 90, 91, 92, 93, 94 ], 
              [ "C", "D", "A", "B", "C" ] 
           ] }

我想执行一个查询来检索“Columns”字段中的第N个值列表:

session.Query<Block>().Where(b => b.Id == "f539770a").Select(b =>b.columns[i]);

我收到以下错误:

  

{“无法将当前JSON对象(例如{\”name \“:\”value \“})反序列化为类型'System.Collections.Generic.List`1 [System.Object]',因为类型需要要正确反序列化的JSON数组(例如[1,2,3])。\ r \ n要修复此错误要么将JSON更改为JSON数组(例如[1,2,3]),要么更改反序列化类型以便它是一个普通的.NET类型(例如,不是像整数这样的基本类型,不是类似于数组或List的集合类型),可以从JSON对象反序列化.JsonObjectAttribute也可以添加到类型中以强制它从JSON对象反序列化。\ r \ nPath'__document_id'。“}

似乎查询正在运行(服务器返回http 200),但是存在客户端反序列化问题。

我错过了什么吗?

谢谢!

更新:

我改变了数据结构,因为错误似乎表明:

public class Column
{
    public List<dynamic> data { get; set; }
}

public class Block
{
    public string Id { get; set; }
    public List<Column> columns { get; set; }
}

存储的文档如下:

{
"Id": "f539770a",
"columns": [
             { "data": [ 95, 96, 97, 98, 99 ] },
             { "data": [ "D", "A", "B", "C", "D" ] }
           ]}

执行此查询后:

session.Query<Block>().Include<Block>(b => b.columns).Where(b => b.parentFileId == dbFileDescriptor.Id).Select(b => b.columns[i])

我没有异常,但是没有加载嵌套数组:

Nested array not loading

1 个答案:

答案 0 :(得分:2)

删除Include。这不是它的用途。 Include用于预加载对其他文档的引用,因此您不必进行多次数据库访问。您可能正在使RavenDB查找Block's及其相应的Column文档。请参阅文档here

session.Query<Block>().Where(b => b.parentFileId == dbFileDescriptor.Id).Select(b => b.data[i]);

修改

如果您要按ID显示某些内容,请使用Load而不是Query

session.Load<Block>("f539770a").data[i];

我确认这适用于使用RavenDB.Tests.Helpers nuget包进行乌鸦单元测试,并使用Shouldly进行断言。

    public class SoQuestion : RavenTestBase
    {
        [Fact]
        public void GetBlock_Success()
        {
            using (var docStore = NewDocumentStore())
            {
                using (var session = docStore.OpenSession())
                {
                    session.Store(new Block
                    {
                        Id = "f539770a",
                        data = new List<List<dynamic>>()
                        {
                            new List<dynamic>()
                            {
                                90,
                                91,
                                92,
                                93,
                                94
                            },
                            new List<dynamic>()
                            {
                                "C",
                                "D",
                                "A",
                                "B",
                                "C"
                            }
                        }
                    });
                    session.SaveChanges();
                }

                docStore.WaitForStaleIndexesToComplete();

                //Act
                var block = GetBlock(docStore);

                //Assert
                block.ShouldNotBe(null);
                block.data.ShouldNotBeEmpty();
            }
        }

        private Block GetBlock(IDocumentStore documentStore)
        {
            using (var session = documentStore.OpenSession())
            {
                return session.Load<Block>("f539770a");
            }
        }

        public class Block
        {
            public string Id { get; set; }
            public List<List<dynamic>> data { get; set; }
        }
    }