Вот, пожалуй, самое простое решение , которое преобразует любые дочерние элементы ITEM
в его атрибуты и воспроизводит все остальное, как есть, при преобразовании имен элементов в любые нужные имена атрибутов:
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<!-- -->
<xsl:strip-space elements="*"/>
<xsl:variable name="vrtfNameMapping">
<item name="SERIALNUMBER" newName="serialNumber"/>
<item name="LOCATION" newName="location"/>
<item name="BARCODE" newName="barcode"/>
</xsl:variable>
<!-- -->
<xsl:variable name="vNameMapping" select=
"document('')/*/xsl:variable[@name='vrtfNameMapping']"/>
<!-- -->
<xsl:template match="node()|@*">
<xsl:copy>
<xsl:apply-templates select="node()|@*"/>
</xsl:copy>
</xsl:template>
<!-- -->
<xsl:template match="ITEM/*">
<xsl:attribute name=
"{$vNameMapping/*[@name=name(current())]/@newName}">
<xsl:value-of select="."/>
</xsl:attribute>
</xsl:template>
</xsl:stylesheet>
когда вышеуказанное преобразование применяется к предоставленному документу XML :
<INVENTORY>
<ITEM>
<SERIALNUMBER>something</SERIALNUMBER>
<LOCATION>something</LOCATION>
<BARCODE>something</BARCODE>
</ITEM>
</INVENTORY>
желаемый результат получен :
<INVENTORY>
<ITEM serialNumber="something" location="something" barcode="something"/>
</INVENTORY>
Обратите внимание на следующее:
Использование правила идентификации
Использование <xsl:strip-space elements="*"/>
Использование переменной vrtfNameMapping
без какой-либо xxx:node-set()
функции расширения.
Тот факт, что мы обрабатываем любое сопоставление между именем и новым именем, а не только простые строчные буквы.