Learn how to a build a cloud-first strategyRegister Now

x
?
Solved

XSL - using CDATA or other to escape message otherwise seen as markup

Posted on 2013-06-25
8
Medium Priority
?
436 Views
Last Modified: 2013-06-25
I'm trying to use CDATA to escape a block of text that would otherwise be interpreted as markup.

I have the following .xsl

  <xsl:template match="Response">
    <Request>
      MI
      <xsl:call-template name="strip-between-tags">
        <xsl:with-param name="str" select="."/>
      </xsl:call-template>        
    </Request>
  </xsl:template>
 
  <xsl:template name="strip-between-tags">
    <xsl:param name="str"/>  
    <xsl:if test="contains($str, '&lt;')">
      <xsl:text disable-output-escaping="yes">&lt;</xsl:text>
      <xsl:value-of select="substring-before(substring-after($str, '&lt;'), '&gt;')"></xsl:value-of>
      <xsl:text disable-output-escaping="yes">&gt;</xsl:text>
      <xsl:call-template name="strip-between-tags">
        <xsl:with-param name="str" select="substring-after($str, '&gt;')"/>
      </xsl:call-template>
    </xsl:if>
    <xsl:if test="not (contains($str, '&lt;'))">
      <xsl:text disable-output-escaping="yes"> &lt;X&gt; </xsl:text>
    </xsl:if>
  </xsl:template>  

    This is my input data that I'm feeding into the xsl:
<CommandRS Version="2003.XML1.0.1">
      <Response>MI&lt;X&gt; X IF SELECT NAME  &lt;CAD&gt;&lt; &gt;</Response>
</CommandRS>
 
 
  Produces output
<CommandRQ Version="2003.XML.0.1">
      <Request>MI<X><CAD>< > <X> </Request>
</CommandRQ>
 

However, the output is erroring out because of the message between the Request tags.
So I tried changing my xsl to include CDATA:

  <xsl:template match="Response">
    <Request>
     <![CDATA[
      
    MI
    <xsl:call-template name="strip-between-tags">
        <xsl:with-param name="str" select="."/>
      </xsl:call-template>
     
        ]]>
    </Request>
  </xsl:template>
 
but this would comment out my template call. Please advise on how I can escape the block of text using CDATA or other method.
 
I also tried
  <xsl:template match="Response">
    <Request>
      <xsl:text><![CDATA[ ]]></xsl:text>
    MI
    <xsl:call-template name="strip-between-tags">
        <xsl:with-param name="str" select="."/>
      </xsl:call-template>

    </Request>
  </xsl:template>
 
but the output never included the "![CDATA[". Not sure how to implement this into the xsl
0
Comment
Question by:badtz7229
  • 3
  • 3
  • 2
8 Comments
 
LVL 19

Expert Comment

by:zc2
ID: 39275141
Never tried that, but may be the "cdata-section-elements" attribute of the xsl:output element might help?
<xsl:output method="xml" cdata-section-elements="Request"/>
0
 

Author Comment

by:badtz7229
ID: 39275210
zc2:
how do you incorporate that. i just added that line in my   <xsl:template match="Response"> but it didn't like it.
0
 
LVL 60

Assisted Solution

by:Geert Bormans
Geert Bormans earned 1000 total points
ID: 39275218
it is on the xsl:output you need to put that, have done that a lot, works well

  <xsl:output indent="yes" cdata-section-elements="Request"/>

(note: xsl:output is a top level element in case you haven't used it)

the result element is what you need to put there

but you also need to remove the disable-output-escaping if you do that

     <xsl:text disable-output-escaping="yes">&gt;</xsl:text>
should be
     <xsl:text>&gt;</xsl:text>
0
What does it mean to be "Always On"?

Is your cloud always on? With an Always On cloud you won't have to worry about downtime for maintenance or software application code updates, ensuring that your bottom line isn't affected.

 
LVL 19

Accepted Solution

by:
zc2 earned 1000 total points
ID: 39275248
Put this xsl:output line right after the first root element's opening tag of the XSLT:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
  <xsl:output indent="yes" cdata-section-elements="Request"/>

Open in new window

0
 

Author Comment

by:badtz7229
ID: 39275474
what's the diff between
<xsl:output method="xml" cdata-section-elements="Request"/>
and
 <xsl:output indent="yes" cdata-section-elements="Request"/>

method versus indent?
0
 
LVL 60

Expert Comment

by:Geert Bormans
ID: 39275506
method says you are creating XML, but that is the default if you output a root element different from <html>, so not really required

indent=yes makes that the output is indented (so easier to view)

it is all different attributes to the output element
the output element organises teh serialisation

In this stylesheet
<xsl:output method="xml" indent="yes" cdata-section-elements="Request"/>
would be equivalent to
<xsl:output indent="yes" cdata-section-elements="Request"/>
0
 

Author Closing Comment

by:badtz7229
ID: 39275632
There was no need for me to remove the disable-output-escaping when i added <xsl:output indent="yes" cdata-section-elements="Request"/>

I saw same output.
0
 
LVL 60

Expert Comment

by:Geert Bormans
ID: 39275754
mmh, I have do disagree with that last statement.
If you see no difference with msxml, then that means msxml does it wrong.
Saxon does it right, there is a little quirk in Xalan too

if you tell the serialiser to make an element having CDATA content, you tell it to put all text nodes in a CDATA section.
BUT... by setting the d-o-e to yes, you tell the serialiser NOT to escape the '<' on output. Essentialy that means that you are outputting a STAGO (start tag opener), not a '<' character. That is not text, so should not be treated as text and the CDATA section should stop before and restart after the '<'. Most processors do that right. I also tested msxml, and it does the wrong thing. But this really is in the grey areas of XSLT.

However, I see no reason why you would leave an erroneous construct in your stylesheet. It makes your stylesheet less portable and unpredictable.
For msxml there is no difference. But I suggest you get rid of the d-o-e in your stylesheet. It would then also do the right thing with other processors
0

Featured Post

How to Use the Help Bell

Need to boost the visibility of your question for solutions? Use the Experts Exchange Help Bell to confirm priority levels and contact subject-matter experts for question attention.  Check out this how-to article for more information.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

This article demonstrates how to create a simple responsive confirmation dialog with Ok and Cancel buttons using HTML, CSS, jQuery and Promises
Create a Windows 10 custom Image with custom task bar and custom start menu using XML for deployment.
In this tutorial viewers will learn how to style a decorative dropcap for the first letter in a paragraph using CSS. In CSS, create a new paragraph class by typing "p.fancy": Then, to style only the first letter of the first sentence, include the ps…
Learn how to create flexible layouts using relative units in CSS.  New relative units added in CSS3 include vw(viewports width), vh(viewports height), vmin(minimum of viewports height and width), and vmax (maximum of viewports height and width).
Suggested Courses
Course of the Month21 days, 5 hours left to enroll

810 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question