smr5
smr5

Reputation: 2793

Parse string in XSLT

I'm doing for-each loop in the XSLT and it's returning me a long string. What I want to do is parse the string .

Here's the code.

<xsl:for-each select="/CAudioFile/CRI/PrivateData/PrivateData/DictionaryEntry">
    <xsl:value-of select="Value" />
</xsl:for-each>

This is the string it's returning:

9702195481, 31201(CCC AGENT)09999051221399561274822396000069522

What I want to do is to get the first portion in one variable:

9702195481, 31201(CCC AGENT)

and replace the comma with a semicolon.

And the second string starts at the end of the first string and it's 20 characters. So it would return

09999051221399561274

I have tried substring, but I get compiler error.

Any suggestions on how I can accomplish this?

Here's the source xml and xslt file.

XML and XSLT File

Here' the screen shot how it looks like now and the format I want.

The format I want Image

I would actually prefer this to generate CSV however, my formatting is not correct that's why I stick with HTML.

Upvotes: 1

Views: 2192

Answers (2)

michael.hor257k
michael.hor257k

Reputation: 116959

If you don't want to end up with one long string concatenating all your DictionaryEntry/Values, then don't do this:

<td>
    <xsl:for-each select="CAudioFile/CRI/PrivateData/PrivateData/DictionaryEntry">
        <xsl:value-of select="Value" />
    </xsl:for-each>
</td>

Try instead:

<td>
    <xsl:value-of select="translate(CAudioFile/CRI/PrivateData/PrivateData/DictionaryEntry[1]/Value, ',', ';')" />
    <xsl:value-of select="CAudioFile/CRI/PrivateData/PrivateData/DictionaryEntry[2]/Value" />
</td>

or perhaps:

<td>
    <xsl:value-of select="translate(CAudioFile/CRI/PrivateData/PrivateData/DictionaryEntry[Key='CD1']/Value, ',', ';')" />
    <xsl:value-of select="CAudioFile/CRI/PrivateData/PrivateData/DictionaryEntry[Key='CD2']/Value" />
</td>

Upvotes: 2

helderdarocha
helderdarocha

Reputation: 23637

This XPath expression will extract the first part of the string if you can consider the ) to be a delimiter (it doesn't occur anywhere else in your candidate strings):

concat(translate(substring-before('9702195481, 31201(CCC ...', ')'),',',';'),')')

This one will get the first 20 characters of the second part:

substring(substring-after('9702195481, 31201(CCC ...', ')'),1,20)

You can use these in your <xsl:value-of select=""> and place it inside a <xsl:variable> to save it in a variable:

 <xsl:for-each select="/CAudioFile/CRI/PrivateData/PrivateData/DictionaryEntry">
        <xsl:variable name="first">
            <xsl:value-of select="concat(translate(substring-before(., ')'),',',';'),')')" />
        </xsl:variable>
        <xsl:variable name="second">
            <xsl:value-of select="substring(substring-after(., ')'),1,20)" />
        </xsl:variable>

        <first-part><xsl:value-of select="$first" /></first-part>
        <second-part><xsl:value-of select="$second" /></second-part>
 </xsl:for-each>

Assuming the example string you provided

9702195481, 31201(CCC AGENT)09999051221399561274822396000069522

is the value of the context node in the for-each (for a certain iteration), it will print this:

<first-part>9702195481; 31201(CCC AGENT)</first-part>
<second-part>09999051221399561274</second-part>

You can verify this transformation in this xslt fiddle

Upvotes: 0

Related Questions