This is the mail archive of the xsl-list@mulberrytech.com mailing list .


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

Re: Convert XML elements with extended attributes into CSV


Hi Xiaocun,

> 1. To place double-quotes around the content, I read
> in the FAQ section Special Characters (under 16.
> Character Escaping) that I should able to use '"' with
> concat().  But when I tried, I get the error "need
> whitespace between attributes".  So I had to use
> '"' instead like:
> concat('"', @Description, '",')
> Is this the best way to do this? 

I'd use " since it's more readable:

  <xsl:value-of select="concat('&quot;', @Description, '&quot;')" />

Whether you like using concat() or having literal text in your
stylesheet is a matter of style and what you're used to.  An
alternative to the above would be:

  <xsl:text />"<xsl:value-of select="@Description" />"<xsl:text />

> 2. Since some of descriptions also contains
> double-quote, such as 1/2"; the double-quote needs to
> be escaped with another double-quote in CSV, so it
> would like 1/2"".  To do that, I was trying to use
> translate():
> translate(@Description, '&#x22;', '&#x22;&#x22;')
> But this does NOT seems to work, did I use translate()
> incorrectly or there is a better way to do string
> replacement?

The translate() function only deals with
single-character-to-single-character replacement.  To get what you
need, you need to use a recursive template to work through the string,
replacing all "s with ""s:

<xsl:template match="node()" mode="escape-CSV" name="escape-CSV">
   <xsl:param name="string" select="." />
   <xsl:choose>
      <xsl:when test="contains($string, '&quot;')">
         <xsl:value-of select="substring-before($string, '&quot;')" />
         <xsl:text>""</xsl:text>
         <xsl:call-template name="escape-CSV">
            <xsl:with-param name="string"
                  select="substring-after($string, '&quot;')" />
         </xsl:call-template>
      </xsl:when>
      <xsl:otherwise>
         <xsl:value-of select="$string" />
      </xsl:otherwise>
   </xsl:choose>
</xsl:template>

To use this template, you need to apply templates in escape-CSV mode
to the node whose value you want to escape:

   <xsl:apply-templates select="@Description" mode="escape-CSV" />

Or if you only want to apply it to a partial node value, then you can
call it by name, setting the $string parameter.
   
I hope that helps,

Jeni

---
Jeni Tennison
http://www.jenitennison.com/



 XSL-List info and archive:  http://www.mulberrytech.com/xsl/xsl-list


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]