簡體   English   中英

序列化/反序列化IPagedList <T> 使用JSON.NET

[英]Serialize/deserialize IPagedList<T> using JSON.NET

我有以下用例,我想使用JSON.net(Newtonsoft.Json)對T的IPagedList進行序列化/反序列化。 這似乎不起作用。 它不會序列化所有項目,僅序列化項目(或使用我自己的ContractResolver,即具有空屬性的對象)。 我正在使用X.PagedList nuget。

一個測試用例:

var list = new List<int>(Enumerable.Range(1, 1000));
var paged = list.AsQueryable().ToPagedList(3, 10);


var json = JsonConvert.SerializeObject(paged); (output: [21,22,23,24,25,26,27,28,29,30])
var obj = JsonConvert.DeserializeObject<PagedList<int>>(json);

當我擴展DefaultContractResolver並覆蓋CreateContract方法時,它反序列化為IPagedList對象,但沒有填充屬性,也沒有項目。。我嘗試覆蓋CreateProperties,但沒有按預期工作。

protected override JsonContract CreateContract(Type objectType)
{
    if (typeof(IPagedList).IsAssignableFrom(objectType))
    {
        return CreateObjectContract(objectType);
    }
   return base.CreateContract(objectType);
}

那么如何才能成功地序列化/反序列化此類?

也許您可以考慮使用內置的LINQ函數.skip().take()

根據我上面的評論,PagedList的回購似乎很長時間沒有得到維護。 在將頭撞牆之前,請嘗試上述內置功能。

PagedList github存儲庫。

跳過樣本

當您序列化IPagedList時,它將序列化所請求頁面的內容/數據,而不會丟失元數據(即FirstItemOnPage,HasNextPage等屬性)。 因此,要克服此問題,您可以創建一個如下所示的匿名類,該類具有兩個屬性

  • 項目保存當前頁面內容
  • metaData保存超級列表元數據。

因此,將代碼的第一部分更改為:

 var list = new List<int>(Enumerable.Range(1, 1000));
 var paged = list.AsQueryable().ToPagedList(3, 10);
 var pagedWithMetaData = new { items = paged, metaData = paged.GetMetaData() };

然后序列化該對象

//Serialize 
var json = JsonConvert.SerializeObject(pagedWithMetaData);

這將為您的示例生成一個帶有metaData的子列表,如下所示:

{"items":[21,22,23,24,25,26,27,28,29,30],"metaData":{"PageCount":100,"TotalItemCount":1000,"PageNumber":3,"PageSize":10,"HasPreviousPage":true,"HasNextPage":true,"IsFirstPage":false,"IsLastPage":false,"FirstItemOnPage":21,"LastItemOnPage":30}}

現在要反序列化,您需要創建三個類:

  • PaginationMetaData類用於封裝元數據,因此當我們反序列化子列表時,其元數據將反序列化為該類型。

  • PaginationEntityClass,其中T:用於封裝匿名類的類,因此當我們對子列表進行反序列化時,其內容和元數據將反序列化為該類型。

  • PaginationEntityStruct,其中T:與PaginationEntityClass相同的結構 ,但這里的T是一個結構,因此它保存結構類型,而不是像int情況那樣的類。

因此,這三個類如下:

public class PaginationMetaData
{
   public int FirstItemOnPage { get; set; }
   public bool HasNextPage { get; set; }
   public bool HasPreviousPage { get; set; }
   public bool IsFirstPage { get; set; }
   public bool IsLastPage { get; set; }
   public int LastItemOnPage { get; set; }
   public int PageCount { get; set; }
   public int PageNumber { get; set; }
   public int PageSize { get; set; }
   public int TotalItemCount { get; set; }
}

public class PaginationEntityClass<T> where T : class
{
   public PaginationEntityClass()
   {
      Items = new List<T>();
   }
   public IEnumerable<T> Items { get; set; }
   public PaginationMetaData MetaData { get; set; }
}

public class PaginationEntityStruct<T> where T : struct
{
   public PaginationEntityStruct()
   {
      Items = new List<T>();
   }
   public IEnumerable<T> Items { get; set; }
   public PaginationMetaData MetaData { get; set; }
}

現在要反序列化,只需要將整數反序列化為PaginationEntityStruct,然后使用StaticPagedList類(PagedList包隨附的類)的第二個構造函數重載來重新創建帶有元數據的子類。

//Deserialize
var result = JsonConvert.DeserializeObject<PaginationEntityStruct<int>>(json);
StaticPagedList<int> lst = new StaticPagedList<int>(
                    result.Items, 
                    result.MetaData.PageNumber, 
                    result.MetaData.PageSize, 
                    result.MetaData.TotalItemCount);

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM