问题
I have a xml file as below, and now I want to use the XSLT to transformer it, keep all the elements and attributes, but if it happen to the attributes with the value started with "SQL:", then execute the sql and replace the attribute value with the resolved SQL(it involve the http://msdn.microsoft.com/en-us/library/533texsx(VS.90).aspx. now I encoutered the issue:how to check if the current node type is attribute, and how to replace the attribute value, I base on the visual studio default template as below:
the example xml file(there are many elements in real):
<DM>
<DV id="SQL:Select something from db">
<Sample aid="SQL:Select something from db">
</Sample>
</DV>
<DV id="SQL:Select something from db">
<Sample aid="SQL:Select something from db">
</Sample>
</DV>
</DM>
default xslt:
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:msxsl="urn:schemas-microsoft-com:xslt" exclude-result-prefixes="msxsl"
xmlns:ms="urn:schemas-microsoft-com:xslt" >
<xsl:output method="xml" indent="yes"/>
<xsl:template match="@* | node()">
<xsl:copy>
<xsl:apply-templates select="@* | node()"/>
</xsl:copy>
</xsl:template>
</xsl:stylesheet>
回答1:
This stylesheet:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:template match="@*|node()">
<xsl:copy>
<xsl:apply-templates select="@*|node()"/>
</xsl:copy>
</xsl:template>
<xsl:template match="@*[starts-with(translate(substring(.,1,4),'sql','SQL'),'SQL:')]">
<xsl:attribute name="{name()}">
<xsl:value-of select="'From SQL!'"/>
</xsl:attribute>
</xsl:template>
</xsl:stylesheet>
Result:
<DM>
<DV id="From SQL!">
<Sample aid="From SQL!"></Sample>
</DV>
<DV id="From SQL!">
<Sample aid="From SQL!"></Sample>
</DV>
</DM>
Note: Don't need to break "identity transform". Add attributes to result tree with xsl:attribute
.
回答2:
Well, you're using one template to match both nodes and attributes. It would be easier to distinguish between them using two separate templates:
<!-- One template for nodes -->
<xsl:template match="node()">
<xsl:copy>
<xsl:apply-templates select="@* | node()"/>
</xsl:copy>
</xsl:template>
<!-- Another template for attributes -->
<xsl:template match="@*">
<!-- Special case for SQL attributes goes here -->
</xsl:template>
To determine if a string starts with a particular substring, you'll want to use the starts-with() function. You can use it like this:
<xsl:if test="starts-with(.,'SQL:')">
<!-- The current node starts with "SQL:" -->
</xsl:if>
来源:https://stackoverflow.com/questions/3289926/how-to-only-convert-an-xml-files-attribute-using-xslt-and-leave-the-other-cont