Reputation: 628
Im trying to build an output file (based on a determined template) having as input another xml.
The xslt code (XSLT 1.0) used to build the output, is "divided" by sections.
I'm skipping the first part of the code... I was "assigning" the variables, for ex:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:date="http://exslt.org/dates-and-times" extension-element-prefixes="date">
<xsl:variable name="securityCode"select="/A/securityCode"/>
<!--and the others variables to I think is are not relevant for my question-->
The xslt (the original code has more sections than this, also I have to use it for different inputs to produce different outputs)
<!--Here we call the templates-->
<xsl:template match="/">
<Header>
<xsl:call-template name="Header">
<xsl:with-param name="securityCode" select = "$securityCode"/>
<xsl:with-param name="generatedTime" select = "$generatedTime"/>
</xsl:call-template>
</Header>
</xsl:template>
<xsl:call-template name="StructureData">
<xsl:with-param name = "payDate"/>
<xsl:with-param name = "amount"/>
<xsl:with-param name = "priRte"/>
<xsl:with-param name = "settlement"/>
<xsl:with-param name = "rate"/>
<xsl:with-param name = "curr"/>
<xsl:with-param name = "rdate"/>
<xsl:with-param name = "ID"/>
<xsl:with-param name = "CID" />
<xsl:with-param name = "Nom" />
</xsl:call-template>
<!--Here we call "define" the templates-->
<xsl:template name = "Header" >
<xsl:param name = "securityCode" />
<xsl:param name = "generatedTime" />
<NHeader>
<MessageID><xsl:value-of select="$securityCode"/></MessageID>
<Timezone>GMT</Timezone>
<GeneratedTime><xsl:value-of select="$generatedTime"/></GeneratedTime>
</NHeader>
</xsl:template>
<xsl:template name = "StructureData" >
<xsl:param name = "payDate"/>
<xsl:param name = "amount"/>
<xsl:param name = "priRte"/>
<xsl:param name = "settlement"/>
<xsl:param name = "rate"/>
<xsl:param name = "curr"/>
<xsl:param name = "rdate"/>
<xsl:param name = "ID"/>
<xsl:param name = "CID" />
<xsl:param name = "Nom" />
<xsl:param name = "securityCode" />
<Data2>
<ID><xsl:value-of select="$ID"/></ID>
<Sett><xsl:value-of select="$settlement"/></Sett>
<BuyOrSell value="Sell"/>
<price value="Price"><xsl:value-of select="$priRte"/></price>
<Cost><xsl:value-of select="$Nom"/></Cost>
<Accrual>
<Cashflow CFLType="Principal">
<Cid><xsl:value-of select="$CID"/></CID>
<CashflowPayment>
<PayDate><xsl:value-of select="$payDate"/></PayDate>
<Amount><xsl:value-of select="$amount"/></Amount>
</CashflowPayment>
</Cashflow>
</Accrual>
</Data2>
</xsl:template>
</xsl:stylesheet>
Finally, my question:
I would like to modify (or rename it) the node value :
<BuyOrSell value="Sell"/>
Depending on the input condition (from an input) variable, let say secutityCode
defined above.
Suppose (securityCode
can be: 1
or 2
)
securityCode=1
then <BuyOrSell value="Sell"/>
securityCode=2
then <BuyOrSell value="Buy"/>
I know how to modify nodes, but once I template as input...actually there are some hints: hint1 hint2 none of these works, or probably I don't how to implement it on my code.
Upvotes: 1
Views: 317
Reputation: 243579
Here is a compact way to do this in XSLT 1.0
(just in a single line like this: <BuyOrSell value="{$vOps[$psecurityCode]}"/>
regardless of the number of different possible op-codes):
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:param name="psecurityCode" select="1"/>
<xsl:variable name="vTxs">
<op>Sell</op>
<op>Buy</op>
</xsl:variable>
<xsl:variable name="vOps" select="document('')/*/xsl:variable[@name='vTxs']/*"/>
<xsl:template match="/">
<BuyOrSell value="{$vOps[$psecurityCode]}"/>
</xsl:template>
</xsl:stylesheet>
When this transformation is applied on any XML document (not used), the wanted, correct result is produced:
<BuyOrSell value="Sell"/>
If you replace the xsl:param
declaration with: <xsl:param name="psecurityCode" select="2"/>
then again the wanted result is produced:
<BuyOrSell value="Buy"/>
II. Explanation
Using AVT (Attribute Value Templates)
Using document('')
to access the stylesheet document and its descendents
Upvotes: 2
Reputation: 167716
If you create an attribute with e.g.
<BuyOrSell>
<xsl:attribute name="value">
<xsl:choose>
<xsl:when test="$securityCode = 1">Sell</xsl:when>
<xsl:when test="$securityCode = 2">Buy</xsl:when>
</xsl:choose>
</xsl:attribute>
</BuyOrSell>
you can implement the condition, although in XSLT 1 that is a rather verbose way.
In general I would suggest to try to use template matching e.g.
<xsl:template match="/A/securityCode[. = 1]">
<BuyOrSell>Sell</BuyOrSell>
</xsl:template>
<xsl:template match="/A/securityCode[. = 2]">
<BuyOrSell>Buy</BuyOrSell>
</xsl:template>
and then further up in the tree processing use <xsl:apply-templates/>
or <xsl:apply-templates select="securityCode"/>
depending on your needs to implement the transformation.
Upvotes: 1