For example I have a xml like
<books>
<book id="1">
<title id="11" name="Basic XML"/>
<price id="12" amount="500"/>
<quantity id="13" number="10"/>
</book>
</books>
Can update the name of the book "Basic XML" to "Basic XSLT" or change any other attributes of any node using XSLT? If yes, can anyone give me some examples on how to do it?
Thanks in advance.
This transformation:
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:my="my:my">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<my:reps>
<repAttr name="name" value="Basic XSLT"/>
<repAttr name="amount" value="300"/>
<repAttr name="number" value="20"/>
</my:reps>
<xsl:strip-space elements="*"/>
<xsl:template match="node()|@*">
<xsl:copy>
<xsl:apply-templates select="node()|@*"/>
</xsl:copy>
</xsl:template>
<xsl:template match=
"@*[name()=document('')/*/my:reps/*/@name]">
<xsl:attribute name="{name()}">
<xsl:value-of select=
"document('')/*/my:reps/*[@name=name(current())]/@value"/>
</xsl:attribute>
</xsl:template>
</xsl:stylesheet>
when applied on the provided XML document:
<books>
<book id="1">
<title id="11" name="Basic XML"/>
<price id="12" amount="500"/>
<quantity id="13" number="10"/>
</book>
</books>
produces the wanted, correct result:
<books>
<book id="1">
<title id="11" name="Basic XSLT"/>
<price id="12" amount="300"/>
<quantity id="13" number="20"/>
</book>
</books>
Explanation:
The identity rule/template copies every node "as-is".
The identity template is overriden by a single template matching any attribute whose name can be found as value of one of the name
attributes of a repAttr
element that is specified in the my:reps
element (parameters embeded in the XSLT stylesheet).
In this case the attribute is re-created (not copied) with the same name and with the new value, specified in the corresponding repAttr
element (its value
attribute).
I cannot "update" the input Xml as XSLT is purely an output driven technology. It creates anew document and cannot modify the existing one.
You could make an almost identical copy but as @Oded comment points out XSLT may be overkill. The xsl would look something like (a modified identity transform)
<xsl:stylesheet version="1.0">
<xsl:template match="@*|node()">
<xsl:copy>
<xsl:apply-templates select="@*|node()"/>
</xsl:copy>
</xsl:template>
<xsl:template match="title/@Name">
<!-- insert logic here to change the value as appropriate -->
</xsl:template>
</xsl:stylesheet>
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With