10/30/11

Invalid Expanded Name LINQ to XML

In the System.Xml.Linq API, the concatenation of the namespace and a local element name creates the expanded name. When an invalid expanded name exception is raised, it can occur when a LINQ to XML query uses an element attribute, and the attribute name that is used is an empty string. For example, with an Xml like this:

<Items>
<item id=”1”>one</item>
<item id=”2”>two</item>
<item>three with no id attribute</item>
</Items>

If you query the document with the following syntax: (get all the items with the attribute id)

var nodes = (from item in Xml.Descendants()
             where item.Attribute(NodeId) != null
             select item).ToList<XElement>();


If the NodeId string variable has no value, the exception of the invalid expanded name will be raised. To address this, we should check that the string is not empty before executing the LINQ query. We can also rewrite the query to something like this:

var nodes = (from item in Xml.Descendants()
             where (!String.IsNullOrEmpty(NodeId) && item.Attribute(NodeId) != null)
             select item).ToList<XElement>();


The IsNUllOrEmpty call prevents the execution of the attribute call when NodeId is empty.

I hope this helps.

10/28/11

How to Clone XDocument

The XDocument class does not implement the ICloneable interface, so there is no Clone method to call. There is however a constructor that allow us to do this. The constructor takes an instance of XDocument and creates a new instance with the same XML structure. This can be done with the following code:

string xmlString = "<items><item/><item/></items>";
..

TextReader tr = new StringReader(xmlString);      
XDocument originalDoc = XDocument.Load(tr);
XDocument cloneDoc = new XDocument(originalDoc);

cloneDoc is a new instance that has the same XML document. Any changes to the cloneDoc does not affect the originalDoc XML document.

I hope this helps.