how to provide variable dynamic value from other template? - xslt-1.0

<xsl:template name="split">
<xsl:param name="list"/>
<xsl:variable name="first">
<xsl:value-of select="substring-before($list,' ')"/>
</xsl:variable>
<xsl:copy-of select="$first"/>
</xsl:template>
<xsl:variable name="test">c0 c1 c2 c3 c4</xsl:variable>
<xsl:variable name="var2>
<xsl:call-template name="split">
<xsl:with-param name="returnvalue">
<xsl:value-of select="$test"></xsl:with-param>
</xsl:call-template>
</xsl:variable>
// processing done
i want to return value from template as c0 then back to template match do processing then again go to split template again return c1 done same processing then back to split template then again processing in match template; depending upon the value of test variable...
How could i retreive these values one by one and process the code..??

This stylesheet will scan forward over your input string:
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="1.0">
<xsl:output method="text"/>
<xsl:variable name="string" select="'c0 c1 c2 c3 c4'"/>
<xsl:variable name="delim" select="' '"/>
<xsl:template match="/">
<xsl:call-template name="wrapper">
<xsl:with-param name="string" select="$string"/>
</xsl:call-template>
</xsl:template>
<xsl:template name="wrapper">
<xsl:param name="string"/>
<xsl:choose>
<!-- handle empty input -->
<xsl:when test=" $string = '' "/>
<!-- handle next token -->
<xsl:when test="contains($string, $delim)">
<xsl:call-template name="process">
<xsl:with-param name="substring" select="substring-before($string,$delim)"/>
</xsl:call-template>
<xsl:call-template name="wrapper">
<xsl:with-param name="string" select="substring-after($string,$delim)"/>
</xsl:call-template>
</xsl:when>
<!-- handle last token -->
<xsl:otherwise>
<xsl:call-template name="process">
<xsl:with-param name="substring" select="$string"/>
</xsl:call-template>
</xsl:otherwise>
</xsl:choose>
</xsl:template>
<xsl:template name="process">
<xsl:param name="substring"/>
<xsl:text>RECEIVED SUBSTRING: </xsl:text>
<xsl:value-of select="$substring"/>
<xsl:text>
</xsl:text>
</xsl:template>
</xsl:stylesheet>
to produce the following output:
RECEIVED SUBSTRING: c0
RECEIVED SUBSTRING: c1
RECEIVED SUBSTRING: c2
RECEIVED SUBSTRING: c3
RECEIVED SUBSTRING: c4

Related

I want to convert XPath value like Z.12.s from Z12s using xslt

Please any one help me on converting XPath value to dot (full stop) separated.
E.g: Z12s to Z. 12.after 1st char need put dot and after 2 char dot then every 2 chars dot but not last value.
If you don't know the length of the input string, you will need to use a recursive named template for this, such as:
<xsl:template name="split-string">
<xsl:param name="string"/>
<xsl:param name="length" select="1"/>
<xsl:value-of select="substring($string, 1, $length)"/>
<xsl:if test="string-length($string) > $length">
<xsl:text>.</xsl:text>
<!-- recursive call -->
<xsl:call-template name="split-string">
<xsl:with-param name="string" select="substring($string, $length + 1)"/>
<xsl:with-param name="length" select="2"/>
</xsl:call-template>
</xsl:if>
</xsl:template>
Demo: https://xsltfiddle.liberty-development.net/pNmC4HF
If your address can be over 90 characters, add more if's to the AddressDetail template according the pattern that is in the template.
<xsl:template match="AddressDetails">
<xsl:copy>
<xsl:apply-templates select="node() | #*">
<xsl:with-param name="address" select="substring(Address, 1, 30)"/>
</xsl:apply-templates>
</xsl:copy>
<xsl:if test="string-length(Address) > 30">
<xsl:copy>
<xsl:apply-templates select="node() | #*">
<xsl:with-param name="address" select="substring(Address, 31, 30)"/>
</xsl:apply-templates>
</xsl:copy>
</xsl:if>
<xsl:if test="string-length(Address) > 60">
<xsl:copy>
<xsl:apply-templates select="node() | #*">
<xsl:with-param name="address" select="substring(Address, 61, 30)"/>
</xsl:apply-templates>
</xsl:copy>
</xsl:if>
<!-- etc. -->
</xsl:template>
<xsl:template match="Address">
<xsl:param name="address"/>
<xsl:copy>
<xsl:apply-templates select="#*"/>
<xsl:value-of select="$address"/>
</xsl:copy>
</xsl:template>
<xsl:template match="node()|#*">
<xsl:copy>
<xsl:apply-templates select="node()|#*"/>
</xsl:copy>
</xsl:template>

I want to split the string stored in a variable and store the obtained values in variable using xslt

<xsl:variable name="AAM" select="//AAM"/>
AAM will have string value_1,value_2,value_3,value_4
I then want to split this and store in 4 variables :
seg1,
seg2,
seg3,
seg4
Assuming the below as your input:
<?xml version="1.0" encoding="UTF-8"?>
<body>
<AAM>value_1,value_2,value_3,value_4</AAM>
</body>
An XSLT 2.0 solution to split a comma separated string can be:
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" indent="yes" />
<xsl:variable name="AAM" select="//AAM" />
<xsl:template match="body">
<body>
<xsl:variable name="separator" select="','" />
<xsl:for-each select="tokenize($AAM,$separator)">
<xsl:element name="seg{position()}">
<xsl:value-of select="normalize-space(.)" />
</xsl:element>
</xsl:for-each>
</body>
</xsl:template>
http://xsltransform.net/6qaFCET/1
Edit: (Based on commented)
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" indent="yes" />
<xsl:variable name="AAM" select="//AAM" />
<xsl:template match="body">
<body>
<xsl:variable name="separator" select="','" />
<xsl:for-each select="tokenize($AAM,$separator)">
<xsl:choose>
<xsl:when test="position() = 1">
<xsl:variable name="seg1">
<xsl:value-of select="normalize-space(.)" />
</xsl:variable>
<xsl:copy-of select="$seg1" />
<xsl:text>
</xsl:text>
</xsl:when>
<xsl:when test="position() = 2">
<xsl:variable name="seg2">
<xsl:value-of select="normalize-space(.)" />
</xsl:variable>
<xsl:copy-of select="$seg2" />
<xsl:text>
</xsl:text>
</xsl:when>
<xsl:when test="position() = 3">
<xsl:variable name="seg3">
<xsl:value-of select="normalize-space(.)" />
</xsl:variable>
<xsl:copy-of select="$seg3" />
<xsl:text>
</xsl:text>
</xsl:when>
<xsl:when test="position() = 4">
<xsl:variable name="seg4">
<xsl:value-of select="normalize-space(.)" />
</xsl:variable>
<xsl:copy-of select="$seg4" />
<xsl:text>
</xsl:text>
</xsl:when>
</xsl:choose>
</xsl:for-each>
</body>
</xsl:template>
http://xsltransform.net/6qaFCET/2
Note: following lines can be avoided. It has been added to populate value of variables.
<xsl:copy-of select="$seg2" />
<xsl:text>
</xsl:text>
Assuming you have <AAM>value_1,value_2,value_3,value_4</AAM> and <xsl:variable name="AAM" select="//AAM"/> you can of course use e.g. <xsl:variable name="value-sequence" select="tokenize($AAM, ',')"/> and if then needed access e.g. $value-sequence[1], $value-sequence[2] and so on, thus if you know there are only four values you can declare <xsl:variable name="seq1" select="$value-sequence[1]"/>, <xsl:variable name="seq2" select="$value-sequence[2]"/> and so on. The tokenize function is part of XPath 2 and later so works with XSLT 2 or 3 processors like Saxon 9 or AltovaXML or XmlPrime.
Answering late.
Maybe this is not an exact solution. But this may help you.
This is how I'm able to split a string from an XML node into two variables using XSLT 1.0
<xsl:when test="NodeName">
<xsl:variable name="var" select="NodeName"/>
<xsl:variable name="var1" select="substring-before($var, '=')"/>
<xsl:variable name="var2" select="substring-after($var, '=')"/>
<xsl:value-of select="$var1"/>-
<xsl:value-of select="$var2"/>
</xsl:when>
For Further reference Click Here

XSL I need to remove space

I need to remove the white space between "|"
Example:
|| 3.3 | A | 001 | 2017-03-03T16:57:51 | 01 *20001000000200001437 | Only free ||
I need this output:
||3.3|A|001|2017-03-03T16:57:51|01 *20001000000200001437|Only free||
This is rather awkward to do in XSLT 1.0.
Given the following input:
XML
<root>
<item>|| 3.3 | A | 001 | 2017-03-03T16:57:51 | 01 *20001000000200001437 | Only free ||</item>
</root>
the following stylesheet:
XSLT 1.0
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/>
<xsl:strip-space elements="*"/>
<!-- identity transform -->
<xsl:template match="#*|node()">
<xsl:copy>
<xsl:apply-templates select="#*|node()"/>
</xsl:copy>
</xsl:template>
<xsl:template match="item">
<xsl:copy>
<xsl:variable name="remove-left-spaces">
<xsl:call-template name="remove-spaces">
<xsl:with-param name="text" select="."/>
<xsl:with-param name="delimiter" select="' |'"/>
</xsl:call-template>
</xsl:variable>
<xsl:call-template name="remove-spaces">
<xsl:with-param name="text" select="$remove-left-spaces"/>
<xsl:with-param name="delimiter" select="'| '"/>
</xsl:call-template>
</xsl:copy>
</xsl:template>
<xsl:template name="remove-spaces">
<xsl:param name="text"/>
<xsl:param name="delimiter"/>
<xsl:choose>
<xsl:when test="contains($text, $delimiter)">
<!-- recursive call -->
<xsl:call-template name="remove-spaces">
<xsl:with-param name="text">
<xsl:value-of select="substring-before($text, $delimiter)"/>
<xsl:text>|</xsl:text>
<xsl:value-of select="substring-after($text, $delimiter)"/>
</xsl:with-param>
<xsl:with-param name="delimiter" select="$delimiter"/>
</xsl:call-template>
</xsl:when>
<xsl:otherwise>
<xsl:value-of select="$text"/>
</xsl:otherwise>
</xsl:choose>
</xsl:template>
</xsl:stylesheet>
will return:
Result
<?xml version="1.0" encoding="UTF-8"?>
<root>
<item>||3.3|A|001|2017-03-03T16:57:51|01 *20001000000200001437|Only free||</item>
</root>

How to replace single apostrophe to double apostrophe in XSLT 1.0?

I need to replace a single quote to double quotes.
For example: input = Ram's
So i need a output as Ram''s
How to do in xslt 1.0? Please help me!
Its working for me!
<xsl:template match="name">
<xsl:copy>
<xsl:call-template name="replace">
<!-- Here getting the replaced values -->
<xsl:with-param name="text" select="."/>
</xsl:call-template>
</xsl:copy>
</xsl:template>
<xsl:template name="replace">
<xsl:param name="text"/>
<xsl:param name="searchString">'</xsl:param>
<xsl:param name="replaceString">''</xsl:param>
<xsl:choose>
<xsl:when test="contains($text,$searchString)">
<xsl:value-of select="substring-before($text,$searchString)"/>
<xsl:value-of select="$replaceString"/>
<!-- recursive call -->
<xsl:call-template name="replace">
<xsl:with-param name="text" select="substring-after($text,$searchString)"/>
<xsl:with-param name="searchString" select="$searchString"/>
<xsl:with-param name="replaceString" select="$replaceString"/>
</xsl:call-template>
</xsl:when>
<xsl:otherwise>
<xsl:value-of select="$text"/>
</xsl:otherwise>
</xsl:choose>
</xsl:template>

XSLT1.0 replace multiple occurences of char with <br />

Have the following template that I use with xsl:call-template, but I need to use it to replace a ~ with <br />. I can get it to work with none HTML replacements but not when I try to use <br /> or &NewLine; or
. Any suggestions:
<xsl:template name="replace-substring">
<xsl:param name="original"/>
<xsl:param name="substring"/>
<xsl:param name="replacement" select="''"/>
<xsl:variable name="first">
<xsl:choose>
<xsl:when test="contains($original, $substring)" >
<xsl:value-of select="substring-before($original, $substring)" />
</xsl:when>
<xsl:otherwise>
<xsl:value-of select="$original"/>
</xsl:otherwise>
</xsl:choose>
</xsl:variable>
<xsl:variable name="middle">
<xsl:choose>
<xsl:when test="contains($original, $substring)">
<xsl:value-of select="$replacement" />
</xsl:when>
<xsl:otherwise>
<xsl:text></xsl:text>
</xsl:otherwise>
</xsl:choose>
</xsl:variable>
<xsl:variable name="last">
<xsl:choose>
<xsl:when test="contains($original, $substring)">
<xsl:choose>
<xsl:when test="contains(substring-after($original, $substring),
$substring)">
<xsl:call-template name="replace-substring">
<xsl:with-param name="original">
<xsl:value-of select="substring-after($original, $substring)"/>
</xsl:with-param>
<xsl:with-param name="substring">
<xsl:value-of select="$substring"/>
</xsl:with-param>
<xsl:with-param name="replacement">
<xsl:value-of select="$replacement"/>
</xsl:with-param>
</xsl:call-template>
</xsl:when>
<xsl:otherwise>
<xsl:value-of select="substring-after($original, $substring)" />
</xsl:otherwise>
</xsl:choose>
</xsl:when>
<xsl:otherwise>
<xsl:text></xsl:text>
</xsl:otherwise>
</xsl:choose>
</xsl:variable>
<xsl:value-of select="concat($first, $middle, $last)"/>
</xsl:template>
It's hard to tell what's going on with the first, middle, and last variables but you should be able to just use a literal <br/> in your param...
XML
<test>one~two~three</test>
XSLT 1.0
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output indent="yes"/>
<xsl:strip-space elements="*"/>
<xsl:template match="test">
<xsl:copy>
<xsl:call-template name="replace-char"/>
</xsl:copy>
</xsl:template>
<xsl:template name="replace-char">
<xsl:param name="char" select="'~'"/>
<xsl:param name="replacement"><br/></xsl:param>
<xsl:param name="string" select="."/>
<xsl:variable name="remaining" select="substring-after($string,$char)"/>
<xsl:value-of select="substring-before(concat($string,$char),$char)"/>
<xsl:if test="contains($string,$char)">
<xsl:copy-of select="$replacement"/>
</xsl:if>
<xsl:if test="$remaining">
<xsl:call-template name="replace-char">
<xsl:with-param name="string" select="$remaining"/>
<xsl:with-param name="char" select="$char"/>
<xsl:with-param name="replacement" select="$replacement"/>
</xsl:call-template>
</xsl:if>
</xsl:template>
</xsl:stylesheet>
Output
<test>one<br/>two<br/>three</test>