2010-03-30 16 views
7

que tienen la variable siguiente que acepta un nombre de archivo:¿Cómo crear un documento XML a partir de un objeto .NET?

var xtr = new XmlTextReader(xmlFileName) { WhitespaceHandling = WhitespaceHandling.None }; 
var xd = new XmlDocument(); 
xd.Load(xtr); 

me gustaría cambiarlo para que pueda pasar en un objeto. No quiero tener que serializar el objeto para archivar primero.

¿Esto es posible?

Actualización:

Mis intenciones originales eran para tomar un documento XML, fusionar algunos XSLT (almacenado en un archivo), entonces la salida y la de regreso html ... como esto:

public string TransformXml(string xmlFileName, string xslFileName) 
{ 
    var xtr = new XmlTextReader(xmlFileName) { WhitespaceHandling = WhitespaceHandling.None }; 
    var xd = new XmlDocument(); 
    xd.Load(xtr); 

    var xslt = new System.Xml.Xsl.XslCompiledTransform(); 
    xslt.Load(xslFileName); 
    var stm = new MemoryStream(); 
    xslt.Transform(xd, null, stm); 
    stm.Position = 1; 
    var sr = new StreamReader(stm); 
    xtr.Close(); 
    return sr.ReadToEnd(); 
} 

En el encima del código que estoy leyendo en el xml de un archivo. Ahora lo que me gustaría hacer es simplemente trabajar con el objeto, antes de que se serializara en el archivo.

Así que permítanme ilustrar mi problema utilizando el código

public string TransformXMLFromObject(myObjType myobj , string xsltFileName) 
{ 
    // Notice the xslt stays the same. 
    // Its in these next few lines that I can't figure out how to load the xml document (xd) from an object, and not from a file.... 

    var xtr = new XmlTextReader(xmlFileName) { WhitespaceHandling = WhitespaceHandling.None }; 
    var xd = new XmlDocument(); 
    xd.Load(xtr); 
} 
+1

no sigo lo que están queriendo ¿puedes publicar un mejor ejemplo? –

+0

cambiar * ¿qué * para poder pasar un objeto? El XmlTextReader? quieres pasar un objeto al XmlTextReader? ¿Y qué esperas sacar * *? – Cheeso

+1

@JL: no debe usar 'new XmlTextReader()'. Debería usar 'XmlReader.Create()' en su lugar. –

Respuesta

28

Usted quiere dar vuelta a un objeto .NET arbitraria en una cadena XML serializado? ¡Nada más simple que eso! :-)

public string SerializeToXml(object input) 
{ 
    XmlSerializer ser = new XmlSerializer(input.GetType(), "http://schemas.yournamespace.com"); 
    string result = string.Empty; 

    using(MemoryStream memStm = new MemoryStream()) 
    { 
    ser.Serialize(memStm, input); 

    memStm.Position = 0; 
    result = new StreamReader(memStm).ReadToEnd(); 
    } 

    return result; 
} 

Eso se debe a él :-) Por supuesto, es posible que desee hacer que el espacio de nombres XML predeterminado configurable como un parámetro, también.

¿O desea poder crear un XmlDocument encima de un objeto existente?

public XmlDocument SerializeToXmlDocument(object input) 
{ 
    XmlSerializer ser = new XmlSerializer(input.GetType(), "http://schemas.yournamespace.com"); 

    XmlDocument xd = null; 

    using(MemoryStream memStm = new MemoryStream()) 
    { 
    ser.Serialize(memStm, input); 

    memStm.Position = 0; 

    XmlReaderSettings settings = new XmlReaderSettings(); 
    settings.IgnoreWhitespace = true; 

    using(var xtr = XmlReader.Create(memStm, settings)) 
    { 
     xd = new XmlDocument(); 
     xd.Load(xtr); 
    } 
    } 

    return xd; 
} 
+1

@marc_s: ick! ¡Sin bloques 'que usan'! 'nuevo XmlTextReader()'! -1! –

+0

@John: Estaba arreglando el 'nuevo XmlTextReader()' ... eres demasiado rápido para votar ... –

+0

@John: pero explícame en palabras simples y fáciles de entender el beneficio de 'XmlReader.Create()' contra 'new XmlTextReader()' - nadie ha hecho un punto convincente hasta el momento ..... –

22

Puede serializar directamente en el XmlDocument:

XmlDocument doc = new XmlDocument(); 
XPathNavigator nav = doc.CreateNavigator(); 
using (XmlWriter w = nav.AppendChild()) 
{ 
    XmlSerializer ser = new XmlSerializer(typeof(MyType)); 
    ser.Serialize(w, myObject); 
} 
+0

Creo que el ser.Serializer no acepta el objeto como parámetro? –

+0

uh, nice ... y no hay una cadena intermedia involucrada :) –

+0

Si no fui lo suficientemente claro, el código anterior no se compila porque ser.Serialize tiene algunos parámetros no válidos. De lo contrario, parece una solución elegante. –

3

Ampliando solución @JohnSaunders escribí la siguiente función genérica:

public XmlDocument SerializeToXml<T>(T source) { 
    var document = new XmlDocument(); 
    var navigator = document.CreateNavigator(); 

    using (var writer = navigator.AppendChild()) { 
     var serializer = new XmlSerializer(typeof(T)); 
     serializer.Serialize(writer, source); 
    } 
    return document; 
} 
Cuestiones relacionadas