Tag Archives: XML

Writing Xml without the XmlDeclaration

Consider the following xml file:

<?xml version="1.0" encoding="utf-8" ?>
<!-- some comment -->
<root>
</root>
<!-- another comment -->

If you look at the Well-Formed XML Documents section in the XML specification you see that a well-formed document is defined as:

[1] document ::= prolog element Misc*

Since there is only 1 root element (ever), i assumed that if you Load this file with XmlDocument their would be only one XmlNode in the document ChildNodes. In reality there ChildNodes.Count returns 4.

The simplest way to write this XmlDocument without the declaration would be as following:

XmlWriterSettings xmlWriterSettings = new XmlWriterSettings();
xmlWriterSettings.OmitXmlDeclaration = true;
xmlWriterSettings.Encoding = Encoding.UTF8;
using (XmlWriter writer = XmlWriter.Create(@"result.xml", xmlWriterSettings))
{
 xmlDoc.WriteTo(writer);
}

Generating UTF-8 with System.Xml.XmlWriter

Today i decided to experiment with XmlWriter. The first i wanted to do was set the Encoding to UTF-8.:

StringBuilder stringBuilder = new StringBuilder();
XmlWriter xmlWriter = XmlWriter.Create(stringBuilder);
xmlWriter.Settings.Encoding = Encoding.UTF8;

When i ran this code i recieved the following exception: XmlException was unhandled: The ‘XmlWriterSettings.Encoding’ property is read only and cannot be set. The documentation for the Settings property clearly says:

The XmlWriterSettings object returned by the Settings property cannot be modified. Any attempt to change individual settings results in an exception being thrown.

So i wrote the following:

StringBuilder stringBuilder = new StringBuilder();
XmlWriterSettings xmlWriterSettings = new XmlWriterSettings();
xmlWriterSettings.Encoding = Encoding.UTF8;

XmlWriter xmlWriter = XmlWriter.Create(stringBuilder, xmlWriterSettings);
xmlWriter.WriteStartDocument();
xmlWriter.WriteStartElement("root", "http://www.timvw.be/ns");
xmlWriter.WriteEndElement();
xmlWriter.WriteEndDocument();
xmlWriter.Flush();
xmlWriter.Close();

string xmlString = stringBuilder.ToString();

As you can see: <?xml version=”1.0″ encoding=”utf-16″?><root xmlns=”http://www.timvw.be/ns” /> is still not what i want. Apparently is the Encoding property ignored if the XmlWriter is not using a Stream. So here is my next attempt:

MemoryStream memoryStream = new MemoryStream();
// initialize xmlWriterSettings as above...

XmlWriter xmlWriter = XmlWriter.Create(memoryStream, xmlWriterSettings);
// call the same operations on the xmlWriter as above...

string xmlString = Encoding.UTF8.GetString(memoryStream.ToArray());

Ok, i’m getting close: ?<?xml version=”1.0″ encoding=”utf-8″?><root xmlns=”http://www.timvw.be/ns” />. Luckily enough i knew that the ? (byte with value 239) at the beginning is the BOM. In order to get rid of that byte i had to create my own instance of UTF8Encoding. Finally, i can present some working code:

MemoryStream memoryStream = new MemoryStream();
XmlWriterSettings xmlWriterSettings = new XmlWriterSettings();
xmlWriterSettings.Encoding = new UTF8Encoding(false);
xmlWriterSettings.ConformanceLevel = ConformanceLevel.Document;
xmlWriterSettings.Indent = true;

XmlWriter xmlWriter = XmlWriter.Create(memoryStream, xmlWriterSettings);
xmlWriter.WriteStartDocument();
xmlWriter.WriteStartElement("root", "http://www.timvw.be/ns");
xmlWriter.WriteEndElement();
xmlWriter.WriteEndDocument();
xmlWriter.Flush();
xmlWriter.Close();

string xmlString = Encoding.UTF8.GetString(memoryStream.ToArray());

Accept posted XML data

I remember that i’ve spent a lot of time finding something that allowed me to accept the posted XML data. The solution was very simple:

$data = file_get_contents('php://input');

value-of in an attribute

There were days that i didn’t like XSL because it seemed to be impossible to insert a value inside an attribute. For example:

<form action="<xsl:value-of select="/page/action"/>" method="post">

Today i’ve seen that other people also struggle with this issue. So here is the solution:

<form action="{/page/action}" method="post">
</form>

Playing with XML and XSL

// add stuff to an xml document in php4
$doc = domxml_open_mem($xml);
$root = $doc->document_element();
$inner = $doc->create_element('inner');
$root = $root->append_child($inner);

// add stuff to an xml document in php5
$doc = new DomDocument('1.0', 'UTF-8');
$doc->loadXML($xml);
$root = $doc->getelementsByTagName('resultset')->item(0);
$inner = $doc->createElement('inner');
$root = $root->appendChild($inner);

XHTML does not allow to have an empty list, <ul></ul>. Therefore we need to test first if there are any nodes we want to put in that list. The code to do this looks like:

<xsl:for-each select="//resultset/entity">
  <div class="mainitem">
  <div class="maintitle"><xsl:value-of select="title"/></div>
  <div class="maincontent">
    <xsl:if test="count(items/item) &gt; 0">
      <ul>
        <xsl:for-each select="items/item">
        <li><a href="{link}"><xsl:value-of select="title"/></a></li>
        </xsl:for-each>
      </ul>
    </xsl:if>
  </div>
  </div>
</xsl:for-each>

XSLT annoyances

Today i’ve finally made the switch. My code generates XML and then i translate it to XHTML with XSLT. However, if i write

<textarea name="foo"></textarea>

it will be translated to:

<textarea name="foo"/>.

A not so good workaround is to write: (Notice the space in the xsl:text)

<textarea name="foo"><xsl:text> </xsl:text></textarea>

UPDATE on 2005-01-20 05:42
The solution is to use html as output method instead of xml.

<xsl:output method='html'/>

UPDATE on 2005-01-21 02:15
You may also want to make sure HTML tags do not get transformed:

<xsl:value-of select="attribute[@name='content']" disable-output-escaping="yes"/>

Parsing XML

Today i wrote a little program, VolumeMeter which is usefull for Scarlet customers. It queries mijn.scarlet.be and returns how many megabytes they have used this month.