Application Development Discussions
Join the discussions or start your own on all things application development, including tools and APIs, programming models, and keeping your skills sharp.
cancel
Showing results for 
Search instead for 
Did you mean: 

Special characteristics of XSLT in ABAP/SAP?

Former Member
0 Kudos

Hey everyone,

after my last approach of working with SAP Simple Transformations (https://answers.sap.com/questions/124003/manipulating-incoming-json-with-simple-transformat.html) I'm now working with an incoming XML and a XSLT Transformation. It should use the input XML and transform it into a SAP structure.

My XML (shortened example):

<result>
  <row>
    <idSite>3</idSite>
    <idVisit>5474057</idVisit>
    <actionDetails>
      <row>
        <type>goal</type>
        <goalId>2</goalId>
        <revenue>0</revenue>
        <goalPageId>45316491</goalPageId>
        <serverTimePretty>Feb 12, 2017 23:55:14</serverTimePretty>
        <timestamp>1486943714</timestamp>
      </row>
      ...
    </actionDetails>     
    <searches>0</searches>
    <actions>24</actions>
  </row>
  ...
</result>

My XSLT (also shortened, but the problem is shown):

<xsl:transform version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:sap="http://www.sap.com/sapxsl">
<xsl:strip-space elements="*"/>
<xsl:template match="/">
  <asx:abap xmlns:asx="http://www.sap.com/abapxml" version="1.0">
    <asx:values>
      <RESULT>
        <xsl:for-each select="result/row">
          <VISIT>
            <SERVERDATE> <xsl:value-of select="serverDate"/> </SERVERDATE>
            <USERID>  <xsl:value-of select="userId"/>      </USERID>
            <VISITORTYPE><xsl:value-of select="visitorType"/> </VISITORTYPE>
            <SEARCHES>    <xsl:value-of select="searches"/> </SEARCHES>
            <ACTIONS> <xsl:value-of select="actions"/>  </ACTIONS>
            <xsl:for-each select="actionDetails">
              <xsl:variable name="row" select="row" />
              <ACTIONDETAILS>
                <TYPE> <xsl:value-of select="$row/type"/> </TYPE>
                <URL> <xsl:value-of select="$row/url"/> </URL>
                <GOALNAME><xsl:value-of select="$row/goalName"/></GOALNAME>
                <ITEMS> <xsl:value-of select="$row/items"/> </ITEMS>
                <xsl:for-each select="itemDetails/row">
                  <ITEMDETAILS>
                    <ITEMSKU> <xsl:value-of select="itemSKU"/></ITEMSKU>
                    <ITEMNAME><xsl:value-of select="itemName"/></ITEMNAME>
                  </ITEMDETAILS>
                </xsl:for-each>
              </ACTIONDETAILS>
            </xsl:for-each>
            <RESULT>  <xsl:value-of select="result"/> </RESULT>
            <MESSAGE> <xsl:value-of select="message"/> </MESSAGE>
          </VISIT>
        </xsl:for-each>
      </RESULT>
    </asx:values>
  </asx:abap>
</xsl:template>
</xsl:transform>

Problem: Once it reaches the first xsl:value-of inside of the inner for-each (at TYPE), it crashes and the debugger throws an CX_XSLT_FORMAT_ERROR. Without debugging it just says "Unexpected text for XML-ABAP transformation."

When I validate my files with an online XSLT Validator (http://www.freeformatter.com/xsl-transformer.html), it does work fine.

Now my assumption/question: Are there some SAP-specific rules for XSLT or XPath I need to follow? I would say so, because it works outside of SAP. I tried to find any solution for this, but without success.

Thanks in advance and kind regards

1 ACCEPTED SOLUTION

Former Member
0 Kudos

Got it:

...
<ACTIONDETAILS>
   <xsl:for-each select="actionDetails/row">
         <ACTIONDETAIL>
           <TYPE>              <xsl:value-of select="type"/>               </TYPE>
          ...
          </ACTIONDETAIL>
   </xsl:for-each>
</ACTIONDETAILS>

For creating data for an internal table, I needed a parent node <ACTIONDETAILS> to add a collection of child elements <ACTIONDETAIL>.

I still can't explain though why it validated in both an online validator and the XSLT tester in SAP.

2 REPLIES 2

Former Member
0 Kudos

Got it:

...
<ACTIONDETAILS>
   <xsl:for-each select="actionDetails/row">
         <ACTIONDETAIL>
           <TYPE>              <xsl:value-of select="type"/>               </TYPE>
          ...
          </ACTIONDETAIL>
   </xsl:for-each>
</ACTIONDETAILS>

For creating data for an internal table, I needed a parent node <ACTIONDETAILS> to add a collection of child elements <ACTIONDETAIL>.

I still can't explain though why it validated in both an online validator and the XSLT tester in SAP.

0 Kudos

Please close the question.

PS: from the XML point of view, it's not an error to not have <ACTIONDETAILS>. But you must have it because of ABAP, containing the name of the internal table (by the way you didn't show the description of your target ABAP variable): <ITABNAME><xsl:for-each ...><item>...</item></xsl-for-each></ITABNAME> (name "item" may vary depending on the rule explained in asXML - Mapping of Internal Tables).