SAP CPI: Technical guide to build a single XSLT mapping for multiple input types

Int4 Team
2020-04-21

In this article you will learn:

  • How to create a simple flow to test your XSLT mappings with Postman
  • What are the advantages of using XSLT mapping in CPI
  • How to not repeat almost the same mapping many times and instead be efficient

Introduction

One of the most annoying things in developing integration solutions is to find ourselves in a situation where we need to repeat a similar task many times. For example, you get several similar messages from different source systems and you need to transform them into one common destination structure. Sounds familiar, right?

Creating several almost identical mappings can be a real pain. Not to mention the maintenance overhead when, for instance, the target structure changes – you need to change all the mappings. Nooo!

XSLT – flexibility is a key

What seems like a perfect solution is a technology that doesn’t rely on your source message name or its structure but the actual field names or values. This is where XSLT comes into play and reveals its best features at work.  Look at the example below where we have two source systems sending our system the same information but in two different formats:

<?xml version="1.0" encoding="UTF-8"?>

<Document>

<Header>

<DocID>0000000001</DocID>

<DocDate>15-04-2020</DocDate>

</Header>

<Line>

<LineNo>1</LineNo>

<MatNo>AB0056</MatNo>

<Price>100.00</Price>

</Line>

<Line>

<LineNo>2</LineNo>

<MatNo>CD0078</MatNo>

<Price>20.00</Price>

</Line>

</Document>

Code 1: XML Input from source system 1

<?xml version="1.0" encoding="UTF-8"?>

<Materials>

<Header>

<DocID>0000000001</DocID>

<DocDate>15-04-2020</DocDate>

</Header>

<Material>

<MatNo>MAT_001</MatNo>

<Prc>40.00</Prc>

</Material>

<Material>

<MatNo>MAT_002</MatNo>

<Prc>10.00</Prc>

</Material>

</Materials>

Code 2: XML Input from source system 2

They are different but still, they carry the same information and share most of the structure. It would be nice if you can work with them in one mapping in one flow, rather than create several instances of almost identical flows. You can achieve this in CPI with XSLT mapping. 

Simple CPI flow to test your XSLT

To test this you need to build a simple flow:

Simple flow with HTTPS call and XSLT mapping

Notice that the above flow is a great tool to test any XSLT mapping using for example Postman. You just send HTTPS POST and receive the result of the XSLT transformation. 

You can upload XSLT transformation from your PC or you can create and edit it directly in the CPI XSLT editor.

Select or create XSLT mapping

Pic. 2 Select or create XSLT mapping

XSLT Editor

Pic. 3 XSLT Editor

One mapping to rule them all!

Below you will find a common mapping for the two XMLs from our example. Key to your success in working with multiple input types inside one mapping is the ability of XPATH to try a selection from multiple paths with one statement by using “|” operator. Check variable Lines below, it will contain a sequence of Line or Material depending on the source message. Thanks to that you can then loop over it with one for-each statement no matter what was the source of selection. The same situation when you are selecting a value for <NetPrice> it will be populated with a value from Price or Prc. Nice right? So in simple words, you can ask XPATH to select whatever it will find, from the list you provide. 

<?xml version="1.0" encoding="UTF-8"?>

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xs="http://www.w3.org/2001/XMLSchema" exclude-result-prefixes="xs" version="1.0">

<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/>

<xsl:template match="/">

<xsl:variable name="Lines" select="//Line|//Material"/>

<input>

<xsl:copy-of select="//Header"/>

<xsl:for-each select="$Lines">

<item>

<MatNo>

<xsl:value-of select="MatNo"/>

</MatNo>

<NetPrice>

<xsl:value-of select="Price|Prc"/>

</NetPrice>

</item>

</xsl:for-each>

</input>

</xsl:template>

</xsl:stylesheet>

Code 3. XSLT mapping for two different inputs

It’s time for you to deploy your flow with the above XSLT mapping and put it at work. You can use Postman and send HTTPS POST requests with example XML files to your CPI flow. The result should look like the one below:

<?xml version="1.0" encoding="UTF-8"?>

<input>

   <Header>

      <DocID>0000000001</DocID>

      <DocDate>15-04-2020</DocDate>

   </Header>

   <item>

      <MatNo>MAT_001</MatNo>

      <NetPrice>40.00</NetPrice>

   </item>

   <item>

      <MatNo>MAT_002</MatNo>

      <NetPrice>10.00</NetPrice>

   </item>

</input>

Code 4. XSLT transformation result in HTTPS response 

Why should you consider this approach?

There are several advantages to this approach:

  • You can easily perform common changes
  • You see differences between source messages processing in one place
  • You can introduce a new source system faster
  • You are working with XSLT on CPI, so you have full potential of XSLT 3.0 and XPATH 3.1 at your disposal

I strongly encourage you to explore XSLT as the most powerful tool available on CPI for mapping. Learning can be quite a challenge but it’s for sure worth trying, as I strongly believe it will help you solve most of the complex mapping challenges you will encounter on your projects. 

Read also: SAP CPI- Combine in Sequence vs Combine Aggregation Algorithm

And if you want to learn more about this missing link of your SAP S/4HANA testing strategy, make sure to visit the Int4’s course called “Avoid SAP S/4HANA Project Delays with Third-Party System Service Virtualization” available here: