I've come across an issue where I need to separate a comma separated string into multiple distinct elements. I've found a template to split the string and one to eliminate the duplicates, but I do not know how to merge them.
Input XML:
<?xml version="1.0"?>
<UDANotification>
<ids>31777,31778,31779,31777,31778</ids>
</UDANotification>
My xsl:
<?xml version="1.0" encoding="UTF-8"?>
<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:template match="text()"/>
<xsl:template match="UDANotification">
<parameters>
<xsl:variable name="string" select="ids"/>
<xsl:call-template name="remove-duplicates">
<xsl:with-param name="string" select="translate($string, ' ', '')"/>
<xsl:with-param name="newstring" select="''"/>
</xsl:call-template>
<!--<<xsl:call-template name="tokenize"/>-->
</parameters>
</xsl:template>
<xsl:template name="remove-duplicates">
<xsl:param name="string"/>
<xsl:param name="newstring"/>
<xsl:choose>
<xsl:when test="$string = ''">
<xsl:value-of select="$newstring"/>
</xsl:when>
<xsl:otherwise>
<xsl:if test="contains($newstring,substring-before($string, ','))">
<xsl:call-template name="remove-duplicates">
<xsl:with-param name="string" select="substring-after($string, ',')"/>
<xsl:with-param name="newstring" select="$newstring"/>
</xsl:call-template>
</xsl:if>
<xsl:if test="not(contains($newstring,substring-before($string, ',')))">
<xsl:variable name="temp">
<xsl:if test="$newstring = ''">
<xsl:value-of select="substring-before($string, ',')"/>
</xsl:if>
<xsl:if test="not($newstring = '')">
<xsl:element name="shift"><xsl:value-of select="concat($newstring, ',',substring-before($string, ','))"/></xsl:element>
</xsl:if>
</xsl:variable>
<xsl:call-template name="remove-duplicates">
<xsl:with-param name="string" select="substring-after($string, ',')"/>
<xsl:with-param name="newstring" select="$temp"/>
</xsl:call-template>
</xsl:if>
</xsl:otherwise>
</xsl:choose>
</xsl:template>
<!--
<xsl:template match="UDANotification/ids" name="tokenize">
<xsl:param name="ids" select="*"/>
<xsl:param name="separator" select="','"/>
<xsl:choose>
<xsl:when test="not(contains($ids, $separator))">
<shift>
<xsl:attribute name="id"><xsl:value-of select="normalize-space($ids)"/></xsl:attribute>
</shift>
</xsl:when>
<xsl:otherwise>
<shift>
<xsl:attribute name="id"><xsl:value-of select="normalize-space(substring-before($ids, $separator))"/></xsl:attribute>
</shift>
<xsl:call-template name="tokenize">
<xsl:with-param name="ids" select="normalize-space(substring-after($ids, $separator))"/>
</xsl:call-template>
</xsl:otherwise>
</xsl:choose>
</xsl:template>
-->
</xsl:stylesheet>
The commented part is the one that splits the string and the active one that eliminates duplicates.
The desired result:
<parameters>
<shift id="31777"/>
<shift id="31778"/>
<shift id="31779"/>
</parameters>
Basically splitting the ids string and eliminating the duplicate values. I am forced to use XSLT1.0 and one stylesheet. Any thoughts on how these templates could be merged or if there is a better way to do both the duplicate elimination and split in one template? Thanks.