2009-03-25 6 views
18

Je crée un ASHX qui retourne XML mais attend un chemin quand je faisPossibilité d'écrire XML en mémoire avec XmlWriter?

XmlWriter writer = XmlWriter.Create(returnXML, settings) 

Mais returnXML est juste une chaîne vide en ce moment (devinez qui ne fonctionne pas), mais je dois écrire le XML à quelque chose que je peux ensuite envoyer en tant que texte de réponse. J'ai essayé XmlDocument mais il m'a donné une erreur en attendant une chaîne. Qu'est-ce que j'oublie ici?

Répondre

42

Si vous voulez vraiment écrire dans la mémoire, passer dans un StringWriter ou un StringBuilder comme celui-ci:

using System; 
using System.Text; 
using System.Xml; 

public class Test 
{ 
    static void Main() 
    { 
     XmlWriterSettings settings = new XmlWriterSettings(); 
     settings.Indent = true;   
     StringBuilder builder = new StringBuilder(); 

     using (XmlWriter writer = XmlWriter.Create(builder, settings)) 
     { 
      writer.WriteStartDocument(); 
      writer.WriteStartElement("root"); 
      writer.WriteStartElement("element"); 
      writer.WriteString("content"); 
      writer.WriteEndElement(); 
      writer.WriteEndElement(); 
      writer.WriteEndDocument(); 
     } 
     Console.WriteLine(builder); 
    } 
} 

Si vous voulez écrire directement à la réponse, cependant, vous pouvez passer à HttpResponse.Output qui est un TextWriter à la place:

using (XmlWriter writer = XmlWriter.Create(Response.Output, settings)) 
{ 
    // Write into it here 
} 
2

la meilleure façon de le faire est d'écrire directement dans le flux de sortie de réponse. C'est un flux qui est intégré à ASP.NET pour vous permettre d'écrire n'importe quelle sortie en tant que flux, dans ce cas vous pouvez écrire du XML dessus.

+2

Je suggère d'écrire à la sortie plutôt que OutputStream. Pourquoi prendre la peine de construire un StreamWriter autour d'un Stream lorsque la sortie le fournit déjà? –

+0

Dans ce cas, je suis d'accord que vous avez probablement raison. Je dis cela parce qu'à en juger par l'extrait fourni, il a déjà le document entier stocké comme une chaîne (returnXML), donc la chose la plus simple est d'écrire cette chaîne à Response.Output et d'éviter complètement XmlWriters. – Steve

+0

Non, returnXml était ce que nous espérions passer * dans * l'appel XmlWriter.Create. Je soupçonne qu'il peut tout simplement sortir avec XmlWriter.Create (Response.Output, paramètres) –

2
StringBuilder xml = new StringBuilder(); 
    TextWriter textWriter = new StringWriter(xml); 
    XmlWriter xmlWriter = new XmlTextWriter(textWriter); 

Ensuite, utilisez la xmlwriter faire tout l'écriture xml, et qui écrit directement au StringBuilder.

Edit: Merci au commentaire de Jon Skeet:

StringBuilder xml = new StringBuilder(); 
    XmlWriter xmlWriter = XmlWriter.Create(xml); 
+0

Vous n'avez pas besoin d'utiliser le StringWriter ici - XmlWriter.Create accepte directement un StringBuilder. –

+0

Oh cool, vous avez raison. Je n'ai jamais remarqué ça. Merci. J'ai vérifié Reflector maintenant, et comme je le soupçonnais, un StringWriter est créé en interne. Merci pour la contribution! Je vais modifier ma réponse. – BFree

6

Il manquait quelque chose de mon côté: le rinçage du tampon de XmlWriter:

static void Main() 
{ 
    XmlWriterSettings settings = new XmlWriterSettings(); 
    settings.Indent = true;   
    StringBuilder builder = new StringBuilder(); 

    using (XmlWriter writer = XmlWriter.Create(builder, settings)) 
    { 
     writer.WriteStartDocument(); 
     writer.WriteStartElement("root"); 
     writer.WriteStartElement("element"); 
     writer.WriteString("content"); 
     writer.WriteEndElement(); 
     writer.WriteEndElement(); 
     writer.WriteEndDocument(); 

     writer.Flush(); 

    } 
    Console.WriteLine(builder); 
} 
+0

J'ai perdu des heures avec le même problème avec la sortie vers un StringBuilder avec un XmlWriter. N'oubliez jamais de tirer la chasse d'eau! – Ted

Questions connexes