2016-02-08 38 views
1

我有一個當前接收JSON調用的API,我推送到文件(800KB-1MB)(每次調用1次),並且希望每小時執行一次任務,以獲取所有JSON文件,並將它們合併到一個文件中,以便更好地進行每日/每月分析。合併多個JSON文件Json.NET

每個文件由一組數據組成,所以格式爲[object {property:value,...]。由於這一點,我不能做簡單的連接,因爲它不再是有效的JSON(也不會添加逗號,那麼文件將會是一個集合的集合)。我想盡可能保持內存底部打印,所以我正在查看以下example,並將每個文件推送到流(使用JsonConvert.DeserializeObject(fileContent)反序列化文件;但是,通過這樣做,我我也嘗試使用JArray而不是JsonConvert,將它推到foreach之外的列表中,但提供了相同的結果。如果我將Serialize調用移動到ForEach之外,它可以工作;但是,我擔心在內存中保存了4至6GB的物品。

總之,我最後得到[[object {property:value,...],... [object { property,value,...]],其中我希望的輸出是[object {property:value(file1),... object {property:value(fileN)]。

 using (FileStream fs = File.Open(@"C:\Users\Public\Documents\combined.json", FileMode.CreateNew)) 
     { 
      using (StreamWriter sw = new StreamWriter(fs)) 
      { 
       using (JsonWriter jw = new JsonTextWriter(sw)) 
       { 
        jw.Formatting = Formatting.None; 

        JArray list = new JArray(); 
        JsonSerializer serializer = new JsonSerializer(); 

        foreach (IListBlobItem blob in blobContainer.ListBlobs(prefix: "SharePointBlobs/")) 
        { 
         if (blob.GetType() == typeof(CloudBlockBlob)) 
         { 
          var blockBlob = (CloudBlockBlob)blob; 
          var content = blockBlob.DownloadText(); 
          var deserialized = JArray.Parse(content); 
          //deserialized = JsonConvert.DeserializeObject(content); 
          list.Merge(deserialized); 
          serializer.Serialize(jw, list); 
         } 
         else 
         { 
          Console.WriteLine("Non-Block-Blob: " + blob.StorageUri); 
         } 
        } 
       } 
      } 
     } 

回答

1

在這種情況下,爲了讓處理和內存足跡保持較低,我認爲我會依次連接文件,即使它導致技術上無效的JSON。要稍後反序列化組合文件,可以利用JsonTextReader類中的SupportMultipleContent設置,並通過流處理對象集合,就好像它們是一個完整集合一樣。有關如何執行此操作的示例,請參閱this answer

+0

這看起來正是我所需要的 - 我很驚訝這個問題已經足夠普遍,他們實際上做了這個設置!謝謝。 –

+0

當我第一次遇到它時,我也很驚訝,但它不止一次地派上用場。 –