2011-12-26 7 views
5

Sto riscontrando un problema nella serializzazione xml della raccolta osservabile.XMLSerialize a ObservableCollection

Qui è quello che sto serializzazione:

public enum Status { Pending, Active, Completed, Cancelled } 

public abstract class Entity : INotifyPropertyChanged 
{ 
    ... 
} 

public class UserStory : Entity 
{ 
    public uint StoryID { get; set; } 
    public Status Status { get; set; } 
    ... 
    public ObservableCollection<Task> Tasks { get; set; } 
} 

public class Task : Entity 
{ 
    public uint TaskID { get; set; } 
    ... 
} 

Ecco come ho serializzare:

public static void SerializeObjectToXML<T>(T item, string FilePath) 
{ 
    XmlSerializer xs = new XmlSerializer(typeof(T)); 
    using (StreamWriter wr = new StreamWriter(FilePath)) 
    { 
     xs.Serialize(wr, item); 
    } 
} 

public class Main() 
{ 
    ObservableCollection<UserStory> UserStories { get; set; } 

    void Main() 
    { 
     ... 
     ObservableCollection<object> Document = new ObservableCollection<object>(); 
     Document.Add(UserStories); 
     SerializeObjectToXML<ObservableCollection<object>>(Document , "..."); 
     ... 
    } 
} 

Ma un errore si verifica nella riga xs.Serialize(wr, item); dicendo:

InvalidOperation Eccezione: si è verificato un errore durante la generazione del documento XML. Eccezione interna: Il tipo ScrumPresentor.ObservableCollection`1 [[ScrumPresentor.UserStory, ScrumPresentor, Version = 1.0.0.0, Culture = neutral, PublicKeyToken = null ]] non può essere utilizzato in questo contesto.

Sto usando Visual Studio 2010, l'applicazione WPF in .NET 4.0.

risposta

19

Provare a utilizzare l'attributo di System.Xml.Serialization.XmlInclude. Non sono sicuro di comprendere correttamente l'intento di una raccolta di raccolte, ma supponendo che sia ciò che desideri, ecco una soluzione funzionante. L'uscita segue il codice:

using System.Collections.Generic; 
using System.Collections.ObjectModel; 
using System.ComponentModel; 
using System.IO; 
using System.Xml.Serialization; 

namespace StackoverflowXxmlSerialize 
{ 

    public enum Status { Pending, Active, Completed, Cancelled } 

    [System.Xml.Serialization.XmlInclude(typeof(UserStory))] 
    [System.Xml.Serialization.XmlInclude(typeof(Task))]  
    public abstract class Entity : INotifyPropertyChanged 
    { 
     public event PropertyChangedEventHandler PropertyChanged; 
    } 


    public class UserStory : Entity 
    { 
     public uint StoryID { get; set; } 
     public Status Status { get; set; } 
     public ObservableCollection<Task> Tasks { get; set; } 
    } 

    public class Task : Entity 
    { 
     public uint TaskID { get; set; } 
    } 

    class Util 
    { 
     public static void SerializeObjectToXML<T>(T item, string FilePath) 
     { 
      XmlSerializer xs = new XmlSerializer(typeof(T)); 
      using (StreamWriter wr = new StreamWriter(FilePath)) 
      { 
       xs.Serialize(wr, item); 
      } 
     } 
    } 



    public class TestSerialize 
    { 
     static ObservableCollection<Entity> UserStories { get; set; } 

     public static void RunTest() 
     { 
      UserStories = new ObservableCollection<Entity> { 
       new UserStory { 
       StoryID = 127, 
       Status = Status.Active, 
       Tasks = new ObservableCollection<Task>{new Task { TaskID = 11 }, new Task { TaskID = 12 }} 
       }, 

       new UserStory { 
       StoryID = 128, 
       Status = Status.Cancelled, 
       Tasks = new ObservableCollection<Task>{new Task { TaskID = 13 }, new Task { TaskID = 14 }} 
       }, 

       new UserStory { 
       StoryID = 129, 
       Status = Status.Completed, 
       Tasks = new ObservableCollection<Task>{new Task { TaskID = 9 }, new Task { TaskID = 10 }} 
       }, 
      }; 


      ObservableCollection<ObservableCollection<Entity>> Document 
       = new ObservableCollection<ObservableCollection<Entity>>(); 

      Document.Add(UserStories); 
      Util.SerializeObjectToXML<ObservableCollection<ObservableCollection<Entity>>>(Document, @"d:\tmp\junk.txt"); 

     } 
    } 

} 

Il codice di cui sopra ha prodotto questo file di testo:

<?xml version="1.0" encoding="utf-8"?> 
<ArrayOfArrayOfEntity xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema"> 
    <ArrayOfEntity> 
    <Entity xsi:type="UserStory"> 
     <StoryID>127</StoryID> 
     <Status>Active</Status> 
     <Tasks> 
     <Task> 
      <TaskID>11</TaskID> 
     </Task> 
     <Task> 
      <TaskID>12</TaskID> 
     </Task> 
     </Tasks> 
    </Entity> 
    <Entity xsi:type="UserStory"> 
     <StoryID>128</StoryID> 
     <Status>Cancelled</Status> 
     <Tasks> 
     <Task> 
      <TaskID>13</TaskID> 
     </Task> 
     <Task> 
      <TaskID>14</TaskID> 
     </Task> 
     </Tasks> 
    </Entity> 
    <Entity xsi:type="UserStory"> 
     <StoryID>129</StoryID> 
     <Status>Completed</Status> 
     <Tasks> 
     <Task> 
      <TaskID>9</TaskID> 
     </Task> 
     <Task> 
      <TaskID>10</TaskID> 
     </Task> 
     </Tasks> 
    </Entity> 
    </ArrayOfEntity> 
</ArrayOfArrayOfEntity> 
+0

Grazie, ma fare un lavoro intorno che invece di mettere il 'ObservableCollection ' in 'ObservableCollection ', Creo una classe che contatina la 'ObservableCollection '. Ma il tuo codice funziona davvero. Grazie comunque. Voglio votare la tua risposta ma non posso perché ho almeno bisogno di 15 rappresentanti. –

+0

Puoi fornire il codice per questa classe che hai creato per mettere la collezione osservabile. Sto affrontando lo stesso problema –