ASP.NET Webservice und zirkuläre Verweise

CarnivoreCI

Mitglied
Hallo,

mein Problem ist folgendes;
Mein Objektmodell besteht aus Projekten - Aufgaben und Entwicklern.

An einem Projekt haengt eine AufgabenCollection und eine EntwicklerCollection.

Eine Aufgabe wiederrum hat einen Verweis auf das uebergeordnete Projekt und eine weitere
EntwicklerCollection.

Ein Entwickler hat eine ProjektCollection und eine AufgabenCollection.

Versuche ich nun über einen Webservice einen Entwickler oder ein Projekt serialisiert zurueckzugeben bekomme ich eine Exception:
Code:
System.InvalidOperationException: Beim Generieren des XML-Dokuments ist ein Fehler aufgetreten. ---> System.InvalidOperationException: Beim Serialisieren eines Objekts vom Typ ProTo.BusinessObjects.Developer wurde ein zirkulärer Verweis gefunden.
   bei System.Xml.Serialization.XmlSerializationWriter.WriteStartElement(String name, String ns, Object o, Boolean writePrefixed, XmlSerializerNamespaces xmlns)
   bei Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationWriter1.Write5_Developer(String n, String ns, Developer o, Boolean isNullable, Boolean needType)
   bei Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationWriter1.Write4_Task(String n, String ns, Task o, Boolean isNullable, Boolean needType)
   bei Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationWriter1.Write5_Developer(String n, String ns, Developer o, Boolean isNullable, Boolean needType)
   bei Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationWriter1.Write7_ArrayOfDeveloper(Object o)
   bei Microsoft.Xml.Serialization.GeneratedAssembly.ListOfDeveloperSerializer.Serialize(Object objectToSerialize, XmlSerializationWriter writer)
   bei System.Xml.Serialization.XmlSerializer.Serialize(XmlWriter xmlWriter, Object o, XmlSerializerNamespaces namespaces, String encodingStyle, String id)
   --- Ende der internen Ausnahmestapelüberwachung ---
   bei System.Xml.Serialization.XmlSerializer.Serialize(XmlWriter xmlWriter, Object o, XmlSerializerNamespaces namespaces, String encodingStyle, String id)
   bei System.Xml.Serialization.XmlSerializer.Serialize(XmlWriter xmlWriter, Object o, XmlSerializerNamespaces namespaces, String encodingStyle)
   bei System.Xml.Serialization.XmlSerializer.Serialize(XmlWriter xmlWriter, Object o, XmlSerializerNamespaces namespaces)
   bei System.Xml.Serialization.XmlSerializer.Serialize(TextWriter textWriter, Object o, XmlSerializerNamespaces namespaces)
   bei System.Xml.Serialization.XmlSerializer.Serialize(TextWriter textWriter, Object o)
   bei System.Web.Services.Protocols.XmlReturnWriter.Write(HttpResponse response, Stream outputStream, Object returnValue)
   bei System.Web.Services.Protocols.HttpServerProtocol.WriteReturns(Object[] returnValues, Stream outputStream)
   bei System.Web.Services.Protocols.WebServiceHandler.WriteReturns(Object[] returnValues)
   bei System.Web.Services.Protocols.WebServiceHandler.Invoke()

Nach langem suchen habe ich im Netz ein Dokument gefunden indem es heißt das SOAP kein Problem mit zirkulären Verweisen haette da es Referenzen anlegt und einfach nur Links erstellt.

Wie kann ich nun meinen WebService dazu bekommen mit SOAP zu arbeiten?

Quellcodes sind hier hinterlegt;
http://www.onlyfree.de/php/pasteservice/show.php?id=10014

Danke & Viele Grueße,
CarnivoreCI

//edit: der Link zu dem Dokument; http://download.microsoft.com/downl...C4-AAC1C255A60E/dotnetpro_3_2003_xml_soap.pdf
 
Zuletzt bearbeitet:
Also, (falls es jemanden interessiert oder jemand das gleiche Problem hat)

Ich hab nen Workaround gefunden mit dem die ganze Sache ganz gut funktioniert.

Die erste Problematik ist das NHibernate Collections in ILists speichert (Generische Listen), damit aber der SoapSerializer nicht kann.
Die Lösung dafuer liegt nahe; einfach in eine ArrayList konvertieren.
Code:
public ArrayList ConvertToConcreteList(IList<T> list)
        {
            ArrayList concreteList = new ArrayList();
            foreach (T currentObject in list)
            {
                concreteList.Add(currentObject);
            }

            return concreteList;
        }

Das zweite Problem ist die Serialisierung. Allerdings weiß ich nicht ob das nicht vielleicht noch einfacher geht, aber hier erstmal meine Lösung.

Code:
[WebMethod]
    public XmlDocument GetDeveloperCollection()
    {
        XmlDocument xDoc = new XmlDocument();
        System.Collections.ArrayList developerList = pCore.DataProvider.GetDeveloperCollection();
        MemoryStream ms = new MemoryStream();
        SoapFormatter sf = new SoapFormatter();

        sf.Serialize(ms, developerList);
        string result = Encoding.Default.GetString(ms.ToArray());
        
        xDoc.LoadXml(result);
        return xDoc;
    }

Auf diesem Wege ist es schonmal möglich eine Collection von komplexen Typen zu serialisieren und über einen Webservice zu schicken.

Falls noch jemand eine einfachere Lösung hat kann er sich gern melden!

Danke, Vg und noch nen schoenen Abend;
carni
 
Zurück