I am using SQL Server 2008 and I want to retrieve XML elements and return the element itself and its attributes without any sub elements and without the text(). Eg the following XML has 4 nodes (doc, apple, b, banana):
<doc>
<apple type="bramley"> tasty <b>yum!</b> </apple>
<banana color="yellow" shape="bendy"> nice in smoothies </banana>
</doc>
I would like to return:
<doc/>
<apple type="bramley"/>
<b/>
<banana color="yellow" shape="bendy"/>
Eg doc should be returned without any sub-nodes and apple should be returned without the b sub-node. But the problem is, if I use the SQL Server nodes and query method I can't remove the sub-nodes. Using SQL Server 2008 the closest I have is:
declare @x xml = '<doc>
<apple type="bramley"> tasty <b>yum!</b> </apple>
<banana color="yellow" shape="bendy"> nice in smoothies </banana>
</doc>';
select
c.query('local-name(.)') as Node,
c.query('for $e in . return <xx> {$e/@*} </xx>') as Attr
from @x.nodes('//*') as T(c);
This gets the name of each node (using local-name) and the attributes of the node and returns:
Node Attr
---- ----
doc <xx />
apple <xx type="bramley" />
b <xx />
banana <xx color="yellow" shape="bendy" />
I realize I can process this result, convert Attr to varchar, replace xx by the Node column and convert back to XML. But is there an easier way without string manipulation?
PS: If it helps, I don't mind if the solution uses SQL Server 2008 or SQL Server 2012.