views:

319

answers:

4

I'm trying to create an XML file to conform to Indeed.com's Job Listing XML.

It looks like:

<?xml version="1.0" encoding="utf-8"?> 
<source>  
    <publisher>Super X Job Site</publisher>  
    <publisherurl>http://www.superxjobsite.com&lt;/publisherurl&gt;  
    <job> 
        <title><![CDATA[Sales Executive]]></title> 
        <date><![CDATA[Fri, 10 Dec 2005 22:49:39 GMT]]></date>
        <referencenumber><![CDATA[unique123131]]></referencenumber>      
        <url><![CDATA[http://www.superxjobsite.com/job/123]]&gt;&lt;/url&gt;  
        <company><![CDATA[Big ABC Corporation]]></company> 
        <city><![CDATA[Phoenix]]></city> <state><![CDATA[AZ]]></state>  
        <country><![CDATA[US]]></country> <postalcode><![CDATA[85003]]></postalcode>  
        <description><![CDATA[Some really long job description goes here.]]></description> 
        </job> 
        [ more jobs ...]

Now, right now I have a IEnumberable of "Jobs", which has properties which match each one of the XML elements above.

What is the best way to generate this XML document and return it as an ActionResult in ASP.NET MVC?

One way, is I could construct the XML string manually like:

String xmlDoc = "<?xml version="1.0" encoding="utf-8"?>"; 
xmlDoc += "<source>";  
xmlDoc += "<publisher>Super X Job Site</publisher>";  
xmlDoc += "<publisherurl>http://www.superxjobsite.com&lt;/publisherurl&gt;";  


foreach(Job job in Jobs)
{
    xmlDoc += "<job>";
    xmlDoc += "<description>" + job.Description + "</description>";
    ...
}

While I know this method would work, is there a better way I should be doing this so I can generate this XML?

+2  A: 

You can build it using the System.Xml namespace. Here are a couple of examples:

http://www.csharphelp.com/archives/archive199.html

http://paulsiu.wordpress.com/2007/04/04/creating-a-xml-document-from-scratch-without-using-a-file-in-c/

If you do decide to assemble it from strings, use a StringBuilder object instead.

Robert Harvey
rob u are onfire
I__
A: 
using System.Xml;

...

XmlDocument doc = new XmlDocument();
XmlNode docNode = doc.CreateXmlDeclaration("1.0", "utf-8", null);
doc.AppendChild(docNode);
XmlNode source = doc.CreateElement("source");

XmlNode publisher = doc.CreateElement("publisher");
publisher.InnerText = "Super X Job Site";
source.AppendChild(publisher);

XmlNode publisherUrl = doc.CreateElement("publisherurl");
publisherUrl.InnerText = "http://www.superxjobsite.com";
source.AppendChild(publisherUrl);

foreach(Job job in Jobs)
{
    XmlNode jobNode = doc.CreateElement("job");
    ...
    source.AppendChild(jobNode);

}

doc.AppendChild(source);
x2
I'll delete my post, apparently, within seconds, we had the same idea, though you made a much nicer example :)
Abel
+3  A: 

If you only need to write it out to a stream. I have had success with the XmlWriter. It is much the same approach as the XmlDocument approach but you can avoid a lot of the CreateElements and AppendElements and generally make things more readable. Below is an example of how you may do it, but you would need to find a better way of doing the cdata as I don't think WriteElementString does it for you.

   XmlTextWriter w = new XmlTextWriter(Response.Output);
   w.WriteStartElement("source");
   w.WriteElementString("publisher", "Super X Job Site");
   w.WriteElementString("publisherurl", "http://www.superxjobsite.com");
   foreach(Job job in Jobs)
   {
       w.WriteStartElement("job");
       w.WriteElementString("title", "Super X Job Site");
       ...
       w.WriteEndElement();
   }
   w.WriteEndElement();
   w.Close();
Andrew Cox
+1 for the comparison with XmlDocument: indeed it's easier in many situations (but if you have to traverse — with XPath or otherwise — the nodes while writing, use XmlDocument though).
Abel
+3  A: 

You can also accomplish the same task using LINQ to XML.

using System.Xml.Linq;
...
...
...

XDocument xmlDoc = new XDocument(
                        new XDeclaration("1.0", "utf-16", "true"),
                        new XElement("source",
                            new XElement("publisher","Super X Job Site"),
                            new XElement("publisherurl","http://www.superxjobsite.com")
                        )
                    );
    foreach (Job job in jobs)
    {
        xmlDoc.Element("source").Add(
            new XElement("job",
                new XElement("title", new XCData(job.Title)),
                new XElement("date", new XCData(job.Date.ToShortDateString())),
                new XElement("referencenumber", new XCData(job.ReferenceNumber)),
                new XElement("url", new XCData(job.Url)),
                new XElement("company", new XCData(job.Company)),
                new XElement("city", new XCData(job.City)),
                new XElement("country", new XCData(job.Country)),
                new XElement("description", new XCData(job.Description))
            )
        );
    }
SpartanBeg