Technology Blogs by SAP
Learn how to extend and personalize SAP applications. Follow the SAP technology blog for insights into SAP BTP, ABAP, SAP Analytics Cloud, SAP HANA, and more.
cancel
Showing results for 
Search instead for 
Did you mean: 
franz_forsthofer
Employee
Employee

Partner Directory – Partner Dependent XML Structures and IDs


This blog explains how you can connect communication partners which use different XML structures and IDs with help of the Partner Directory. The Partner Directory entity “Alternative Partner” maps external partner IDs to IDs internally used by the Partner Directory. In the Partner Directory, you can store XSL transformations and XML schemas, so that you can execute partner dependent XSL transformations and XML schema validations in your integration flow. We will explain useful XSL features, like accessing and setting exchange properties and headers and code mappings.

We introduce the features by enhancing the integration flow which we developed in the previous blog Cloud Integration – Partner Directory – Step-by-Step Example.

Alternative Partner ID


The Alternative Partner entity type was introduced in the Partner Directory to cover the following use cases:

  • The Partner Directory allows for the partner ID only certain characters (alphanumeric characters and ‘-‘, ‘.‘,  ‘_‘,  ‘~‘, ‘<‘, ‘>‘ ) and the length of the partner ID is restricted to 60 characters. The sender and receiver systems of a partner network however may use IDs which do not follow the restrictions for the partner ID. With the Alternative Partner entity you can define a mapping between the IDs used in the partner systems and the partner IDs used in the Partner Directory.

  • Two partners may use different ID values although they refer to the same instance. With the Alternative Partner entity you can map the different external IDs to the same partner ID internally used by the Partner Directory.

  • Two partners may use the same ID value although they refer to different instances. The Alternative Partner entity helps you to map the non-unique external IDs to unique partner IDs internally used in the Partner Directory.


We call the IDs which are used in the partner systems external or alternative IDs and we use for the partner IDs internally used by the Partner Directory the term PD partner IDs.

The Alternative Partner entity type has the following four fields:

  • Agency: Name of organization that defines the identification scheme and issues IDs for the objects to be identified; the Agency can also be the sender partner defining the external IDs; the length of the field is restricted to 120 characters.

  • Scheme: The reference framework within which objects are uniquely identified by names; an agency may provide IDs in different formats, for example BIC (ISO 9362) defines codes with either 8 or 11 characters; the length of the field is restricted to 120 characters.

  • Id: An ID or name that identifies the object within the given scheme, unique within the specified Agency and Scheme value; this Id we call here external ID or alternative ID; the length of the field is restricted to 60 characters.


 

  • Pid: the PD partner ID which is mapped to the alternative ID


The Alternative Partner entity type is designed in such a way that an entry can either be uniquely identified via the Agency, Scheme and Id value or by the Agency, Scheme, and Pid value. This does mean, if you know the Agency, Scheme and Id value of an entry, then you can look-up the corresponding Pid value. Or if you know the Agency, Scheme, and Pid value you can look-up the corresponding Id value.

In a script step of an integration flow you can execute the queries as shown in the following Groovy script:
def service = ITApiFactory.getApi(PartnerDirectoryService.class, null);
def agency = <agency either constant or determined via property or other means>
def scheme = <scheme either constant or determined via property or other means>
def id = <alternative partner ID determined via property filled from message>
// look-up PD partner ID for the alternative partner ID
def partnerId = service.getPartnerId(agency, scheme, id);
// look-up alternative partner ID for the PD partner ID
def alternativePartnerId = service.getAlternativePartnerId(agency, scheme, parnterId);

Groovy Script 1: Looking-up the PD Partner Id for an Altnernative Partner Id, or Looking-up the Alternative Partner Id for a PD Partner Id

Partner Dependent XSL Transformartion and XML Schema Validation


In a scenario where many partners are communicating with each other, it is very likely that not all partners use the same XML structure for the message exchange. Therefore, XSL transformations must be executed to transform the messages from the sender structures to the receiver structures. Typically, the transformation from a sender message to a receiver message is split into two steps. The sender message is first transformed to a common internal structure and in a second transformation the internal message is transformed to the receiver structure. The two-transformation approach helps to reduce the number of necessary XSL transformations.

Suppose you have 10 sender partners and 10 receiver partners, which all require different message structures. If you write transformations which directly transform the sender structures to the receiver structures, you will need 100 transformations. With the two-transformation approach, you only need 20 transformations.

It is also good practice to validate a message as soon as it reaches a system. We will use XML documents in our example scenario and will validate the XML documents with XML Schemas.

Example Scenario


We enhance the scenario given in the previous blog Cloud Integration – Partner Directory – Step-by-Step Example. The following diagram gives an overview about our example scenario.



Diagram 1: Example Scenario

We have two sender partners with the PD partner IDs “Sender_BASIC” and “Sender_OAUTH” and two receiver partners with the PD partner IDs “Receiver_1” and “Receiver_2”. The sender partners send messages via the SAP Cloud Integration to the receiver partners.

New in comparison to the previous blog is, that

  • all four partners use different XML structures for their messages (the above diagram contains example messages of each partner),

  • all partners use IDs different from the PD partner IDs to identify the other communication partners (see the diagram above)

  • there is a new field “Currency” in the messages where the sender partners use the Currency values “$” and “” whereas the receiver partners expect the Currency values “USD” and “EURO” (see the example messages in the above diagram)


Partner “Sender_BASIC”, “Receiver_1”, and “Receiver_2” use the IDs of a standard Agency for their communication partners. We call this standard Agency “AgencyXYZ”. An example for such a standard agency is BIC (ISO 9362). The following table shows how the IDs of the Agency “AgencyXYZ” map to the PD partner IDs.
























ID of AgencyXYZ PD partner ID
Main Sender Sender_BASIC
Sender Company XYZ Sender_OAUTH
Receiver Premium Receiver_1
Receiver 2 Receiver_2


Table 1: Mapping IDs of Agency “AgencyXYZ” to PD Partner IDs

The sender partner “Sender_OAUTH” uses his own IDs for the communication partners. We call his ID agency “Sender_OAUTH_Agency”. The following table shows how the IDs of this agency map to the PD partner IDs.




















ID of Sender_OAUTH_Agency PD partner ID
self Sender_OAUTH
Receiver 1 Receiver_1
Receiver Premium Receiver_2


Table 2: Mapping between IDs of Agency “Sender_OAUTH_Agency” and PD Partner IDs

Note, that the agencies “AgencyXYZ” and “Sender_OAUTH_Agency” use the ID “Receiver Premium” for different partners (“Receiver_1”, “Receiver_2”).

To establish the communication between the partners, the Partner Directory Integration Flow must solve three mapping problems:

  • Mapping of agency partner IDs to PD partner IDs (-> Alternative Partner entity)

  • XML structure transformation (-> sender and receiver XSL transformation)

  • Code mapping (“$” -> “USD”, “€” -> “EURO”, via XSL feature “document”)


Mapping of Agency Partner IDs to PD Partner IDs


The Mapping of the agency partner IDs to the PD partner IDs will be done with help of Partner Directory entries for the Alternative Partner entity. The following table shows which entries we will create.




















































Agency Scheme Id Pid
AgencyXYX LONG Main Sender Sender_BASIC
AgencyXYX LONG Sender Company XYZ Sender_OAUTH
AgencyXYZ LONG Receiver Premium Receiver_1
AgencyXYZ LONG Receiver 2 Receiver_2
Sender_OAUTH_Agency Sender_OAUTH_Scheme self Sender_OAUTH
Sender_OAUTH_Agency Sender_OAUTH_Scheme Receiver 1 Receiver_1
Sender_OAUTH_Agency Sender_OAUTH_Scheme Receiver Premium Receiver_2


Table 3: Alternative Partner Entries in the Partner Directory

We use the fixed scheme value “LONG” for the agency “AgencyXYZ” and the fixed scheme value “Sender_OAUTH_Scheme” for the agency “Sonder_OAUTH_Agency”. Different scheme values for an agency would be necessary, if a partner uses different schemes of the same agency.

For determining dynamically which agency and scheme a partner is using we will also add the following String Parameter entries into the Partner Directory.

















































Pid Id Value
Sender_BASIC AGENCY AgencyXYZ
Sender_BASIC SCHEME LONG
Sender_OAUTH AGENCY Sender_OAUTH_Agency
Sender_OAUTH SCHEME Sender_OAUTH_Scheme
Receiver_1 AGENCY AgencyXYZ
Receiver_1 SCHEME LONG
Receiver_2 AGENCY AgencyXYZ
Receiver_2 SCHEME LONG


Table 4: String Parameter Entries for Dynamic Access of the Agency and Scheme of a Partner

XML Structure Transformation – Code Mapping – Partner Directory URI


This sub-chapter shows example XSL transformations from which you can learn

  • how you can use XSL transformations for XML structure transformations

  • how XSL documents contained in the Partner Directory can reference other Partner Directory XSL documents via Partner Directory URIs

  • how you can set exchange properties and headers within an XSL transformation

  • how you can access exchange properties and headers in an XSL transformation

  • how you use the XSL “document” function to make code mappings


The message structure transformation from the sender XML structures to the receiver XML structures will be done in two mapping steps, as already discussed previously. The intermediate XML structure is represented by the following example XML payload.
<Message>
<Content>test</Body>
<Currency>USD</Currency>
</Message>

Payload 1: Payload Representing the Intermediate XML Structure

The intermediate payload does not contain the sender partner ID or receiver partner ID. These IDs will be stored in exchange properties; see the sender XSL transformations below.

The code mapping from the sender currency codes to the receiver currency codes (“$” -> “USD”, “€” -> “EURO”) will be part of the first mapping by using the XSL “document” feature (see sender XSL transformations below).

For each partner, we need an XSL transformation. For each sender partner we need an XSL transformation which maps the sender XML structure to the intermediate XML structure (called “Sender XSL Transformation”). For each receiver partner we need an XSL transformation which maps the intermediate XML structure to the receiver XML structure (called “Receiver XSL Transformation”).

It is good practice to reuse common parts of XSL transformations. Therefore the Partner Directory supports that XSL documents stored in the Partner Directory can reference other XSL documents or XML Documents of the Partner Directory (using the “xsl:import” or “document” feature; see XSL documents below). The referenced document can be specified by the Partner Directory URI. This URI has the following format:
pd:<PD partner ID>:<Id>:Binary

Format of the Partner Directory URI

where PD partner ID and Id identify a Binary Parameter of the Partner Directory.

The following XSL document “xsl_util” contains utility methods which are referenced by the Sender XSL Transformations (see below).
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:hci="http://sap.com/it/"
xmlns:main="https://main.com/"
exclude-result-prefixes="hci">

<xsl:param name="exchange"/>

<xsl:variable name="CurrencyCodes" select="document('pd:GenericPartner:CurrencyCodes:Binary')"/>

<xsl:template name="transform_currency_code">
<xsl:param name="sender_currency_code" />
<Currency><xsl:value-of select="$CurrencyCodes/LookUp/Entry[SenderCode=$sender_currency_code]/ReceiverCode"/></Currency>
</xsl:template>

<xsl:template name="set_property">
<xsl:param name="property_name" />
<xsl:param name="property_value" />
<xsl:value-of select="hci:setProperty($exchange, $property_name, $property_value)"/>
</xsl:template>

</xsl:stylesheet>

XSL Document “xsl_util”: XSL Document Containing Utility Templates

With the template “set_property” you can set exchange properties within an XSL transformation. It is also possible to set headers with the function

“hci:setHeader($exchange; <header name>, <header value>)”

Use the setting of exchange properties and headers within the XSL transformation instead of setting them via Content Modifier and XPath expression when you have to use an XSL transformation for XML structure transformation. You will gain performance because the source XML document is then parsed only once.

The template “tansform_currency_code” maps the sender currency codes (“$” and “€”) to the receiver currency codes (“USD” and “EURO”).   It uses the document referenced with the variable “CorrencyCodes” stored in the Partner Directory with  the URI pd:GenericPartner:CurrencyCodes:Binary”.

We store the XML document “CurrencyCodes” and the XSL Document “xsl_util” for the generic partner ID “GenericPartner” because these documents are relevant for all sender partners.
<?xml version = "1.0" encoding = "UTF-8"?>
<LookUp>
<Entry>
<SenderCode>$</SenderCode>
<ReceiverCode>USD</ReceiverCode>
</Entry>
<Entry>
<SenderCode>€</SenderCode>
<ReceiverCode>EURO</ReceiverCode>
</Entry>
</LookUp>

XML Document “CurrencyCodes”: Mapping between Sender Currency Codes and Receiver Currency Codes

The following four documents show the XSL documents containing the main parts of the Sender and Receiver XSL Transformations. The sender XSL documents reference the XSL Document “xsl_util” via the Partner Directory URI pd:GenericPartner:xsl_util:Binary. Beside the structure transformation to the intermediate XML structure, the Sender XSL Mappings set the agency sender ID and receiver ID in the exchange properties SENDER_ID and RECEIVER_ID.  The Receiver XSL Mapping documents show how you can access exchange properties in an XSLT (In a similar way you can also access exchange headers, not shown). The Receiver XSL Transformations assume that in the exchange properties EXTERNAL_SENDER_ID and EXTERNAL_RECEIVER_ID the correct sender and receiver IDs of the receiver agencies are available.
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:hci="http://sap.com/it/"
xmlns:main="https://main.com/"
exclude-result-prefixes="hci">

<xsl:import href="pd:GenericPartner:xsl_util:Binary"/>

<xsl:output method="xml" encoding="UTF-8" indent="no" />

<xsl:template match="/">
<Message>
<xsl:apply-templates/>
</Message>
</xsl:template>

<xsl:template match="Sender">
<xsl:call-template name="set_property">
<xsl:with-param name="property_name">SENDER_ID</xsl:with-param>
<xsl:with-param name="property_value" select="."/>
</xsl:call-template>
</xsl:template>

<xsl:template match="Receiver">
<xsl:call-template name="set_property">
<xsl:with-param name="property_name">RECEIVER_ID</xsl:with-param>
<xsl:with-param name="property_value" select="."/>
</xsl:call-template>
</xsl:template>

<xsl:template match="main:Body">
<Content><xsl:value-of select="."/></Content>
</xsl:template>

<xsl:template match="Currency">
<xsl:call-template name="transform_currency_code">
<xsl:with-param name="sender_currency_code" select="."/>
</xsl:call-template>
</xsl:template>

</xsl:stylesheet>

XSL Document “Sender XSL Transformation for Sender_BASIC”
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:hci="http://sap.com/it/"
xmlns:self="https://self.com/"
exclude-result-prefixes="hci">

<xsl:import href="pd:GenericPartner:xsl_util:Binary"/>

<xsl:output method="xml" encoding="UTF-8" indent="no" />

<xsl:template match="/">
<Message>
<xsl:apply-templates/>
</Message>
</xsl:template>

<xsl:template match="self:SenderId">
<xsl:call-template name="set_property">
<xsl:with-param name="property_name">SENDER_ID</xsl:with-param>
<xsl:with-param name="property_value" select="."/>
</xsl:call-template>
</xsl:template>

<xsl:template match="self:ReceiverId">
<xsl:call-template name="set_property">
<xsl:with-param name="property_name">RECEIVER_ID</xsl:with-param>
<xsl:with-param name="property_value" select="."/>
</xsl:call-template>
</xsl:template>

<xsl:template match="self:Content">
<Content><xsl:value-of select="."/></Content>
</xsl:template>

<xsl:template match="self:Currency">
<xsl:call-template name="transform_currency_code">
<xsl:with-param name="sender_currency_code" select="."/>
</xsl:call-template>
</xsl:template>

</xsl:stylesheet>

XSL Document “Sender XSL Transformation for Sender_OAUTH”
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:param name="EXTERNAL_SENDER_ID"/> <!-- exchange property containing the sender ID set by the script step -->
<xsl:param name="EXTERNAL_RECEIVER_ID"/> <!-- exchange property containing the receiver ID set by the script step -->


<xsl:output method="xml" encoding="UTF-8" indent="no" />

<xsl:template match="/">
<Doc>
<SId><xsl:value-of select="$EXTERNAL_SENDER_ID"/></SId>
<RId><xsl:value-of select="$EXTERNAL_RECEIVER_ID"/></RId>
<xsl:apply-templates/>
</Doc>
</xsl:template>


<xsl:template match="Content">
<Body><xsl:value-of select="."/></Body>
</xsl:template>

<xsl:template match="Currency">
<Currency><xsl:value-of select="."/></Currency>
</xsl:template>

</xsl:stylesheet>

XSL Document “Receiver XSL Transformation for Receiver_1”
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:param name="EXTERNAL_SENDER_ID"/> <!-- exchange property containing the sender ID set by the script step -->
<xsl:param name="EXTERNAL_RECEIVER_ID"/> <!-- exchange property containing the receiver ID set by the script step -->


<xsl:output method="xml" encoding="UTF-8" indent="no" />

<xsl:template match="/">
<Message>
<SId><xsl:value-of select="$EXTERNAL_SENDER_ID"/></SId>
<RId><xsl:value-of select="$EXTERNAL_RECEIVER_ID"/></RId>
<xsl:apply-templates/>
</Message>
</xsl:template>


<xsl:template match="Content">
<Body><xsl:value-of select="."/></Body>
</xsl:template>

<xsl:template match="Currency">
<Currency><xsl:value-of select="."/></Currency>
</xsl:template>

</xsl:stylesheet>

XSL Document “Receiver XSL Transformation for Receiver_2”

XSD Documents


We want to validate the XML payloads which are sent to the integration flow by the different sender partners. We store for each sender partner a XML schema in the Partner Directory so that we can dynamically access the partner dependent XML schema in the integration flow.

Like the XSL documents, Partner Directory XSD documents can reference other Partner Directory XSD documents via the “import” and “include” statement using the Partner Directory URI. See line

<import namespace="https://main.com/" schemaLocation="pd:Sender_BASIC:core_xsd:Binary" />

in the following XSD document for the sender “Sender_BASIC”.
<?xml version="1.0" encoding="UTF-8"?>
<schema xmlns="http://www.w3.org/2001/XMLSchema" targetNamespace="https://main.com/" xmlns:tns="https://main.com/" >
<element name="Body" type="string"/>
</schema>

XSD Document “core_xsd” for sender “Sender_BASIC”
<?xml version="1.0" encoding="UTF-8"?>
<schema xmlns="http://www.w3.org/2001/XMLSchema" xmlns:main="https://main.com/">
<import namespace="https://main.com/" schemaLocation="pd:Sender_BASIC:core_xsd:Binary" />

<element name="Document">
<complexType>
<sequence>
<element name="Sender" type="string" />
<element name="Receiver" type="string" />
<element ref="main:Body" />
<element name="Currency">
<simpleType>
<restriction base="string">
<enumeration value="$" />
<enumeration value="€" />
</restriction>
</simpleType>
</element>
</sequence>
</complexType>
</element>
</schema>

XSD Document for sender “Sender_BASIC”
<?xml version="1.0" encoding="UTF-8"?>
<schema xmlns="http://www.w3.org/2001/XMLSchema" targetNamespace="https://self.com/"
elementFormDefault="qualified">

<element name="Message">
<complexType>
<sequence>
<element name="SenderId" type="string" />
<element name="ReceiverId" type="string" />
<element name="Content" type="string" />
<element name="Currency">
<simpleType>
<restriction base="string">
<enumeration value="$" />
<enumeration value="€" />
</restriction>
</simpleType>
</element>
</sequence>
</complexType>
</element>
</schema>

XSD Document for sender “Sender_OAUTH”

Integration Flow


We now explain step by step how the integration flow created in the blog Cloud Integration – Partner Directory – Step-by-Step Example must be enhanced for our new example scenario.

The following screen shot shows the integration flow steps which we will create.



Partner Directory Integration Flow

Step 1: Remove Old Steps


Remove all steps from the integration flow except the sender HTTPS channel and the receiver SOAP channel.

Step 2: Script “Sender PD Partner ID From User”


Create a new Groovy script step with the name “Sender PD Partner ID From User” containing the following Groovy script.
import com.sap.gateway.ip.core.customdev.util.Message;
import com.sap.it.api.pd.PartnerDirectoryService;
import com.sap.it.api.ITApiFactory;
def Message processData(Message message) {
def service = ITApiFactory.getApi(PartnerDirectoryService.class, null);
if (service == null){
throw new IllegalStateException("Partner Directory Service not found");
}
// logged-in user from header "SapAuthenticatedUserName"
def headers = message.getHeaders();
def user = headers.get("SapAuthenticatedUserName");
if (user == null){
throw new IllegalStateException("User is not set in the header 'SapAuthenticatedUserName'")
}

// sender partner ID assigned to user
def senderPid = service.getPartnerIdOfAuthorizedUser(user);
if (senderPid == null){
throw new IllegalStateException("No partner ID found for user "+user);
}

// set "SENDER_PID" property
message.setProperty("SENDER_PID", senderPid );

// header for dynamic sender XSD selection
message.setHeader("SENDER_XSLT","pd:"+senderPid+":SENDER_XSLT:Binary");

// header for dynamic sender XSLT selection
message.setHeader("SENDER_XSD","pd:"+senderPid+":SENDER_XSD:Binary");

return message;
}

Groovy Script 2: “Sender PD Partner ID From User”

The script determines from the logged-in user provided in the header "SapAuthenticatedUserName" the PD partner ID and stores the PD partner ID in the exchange property “SENDER_PID”, and additionally sets the “SENDER_XSLT” and “SENDER_XSD” header containing the Partner Directory URI for the Sender XSL Transformation and the Sender XML schema which are later used in the “XML Validator” and “Sender XSL Transformation” step.

Step 3: XML Validator


Create a XML Validator step with the name “XML Validator” and enter in the field “XML Schema” of the “Validation” tab the value

${header.SENDER_XSD}

This means that the XML Validator step is reading dynamically from the header “SENDER_XSD” the Partner Directory URI for accessing the sender partner dependent XSD document.

Step 4: Sender XSL Transformation


Create a XSLT Mapping step with name “Sender XSL Transformation”. In the “Processing” tab select for the “Source” field the option “Header” and enter the value “SENDER_XSLT” in the “Header Name” field as shown in the following screen shot.



Screen Shot 1: Processing Properties of the “Sender XSL Transformation” Step

The “Sender XSL Transformation” step is reading dynamically from the header “SENDER_XSLT” the Partner Directory URI of the sender partner dependent XSL transformation.

The sender XSL transformation transforms the sender XML structure to the intermediate XML structure and sets the properties “SENDER_ID” and “RECEIVER_ID” containing the sender agency ID values for the sender and receiver. See previous chapter “XML Structure Transformation – Code Mapping – Partner Directory URI”.

Step 5: Script


Create a Groovy script step with name “Script” containing the following Groovy script.
import com.sap.gateway.ip.core.customdev.util.Message;
import java.util.HashMap;
import com.sap.it.api.pd.PartnerDirectoryService;
import com.sap.it.api.ITApiFactory;
def Message processData(Message message) {
def service = ITApiFactory.getApi(PartnerDirectoryService.class, null);
if (service == null){
throw new IllegalStateException("Partner Directory Service not found");
}
def properties = message.getProperties();
// get sender PD partner ID from "SENDER_PID" property; set by
def senderPid = properties.get("SENDER_PID");

// get agency and scheme of sender
def senderAgency = service.getParameter("AGENCY", senderPid , String.class);
if (senderAgency == null){
throw new IllegalStateException("AGENCY parameter not found in the Partner Directory for the partner ID "+senderPid );
}
def senderScheme = service.getParameter("SCHEME", senderPid , String.class);
if (senderScheme == null){
throw new IllegalStateException("SCHEME parameter not found in the Partner Directory for the partner ID "+senderPid );
}

// senderId is the external sender ID used by the sender partner
def senderId = properties.get("SENDER_ID");
if (senderId == null){
throw new IllegalStateException("Sender ID is not set in the property 'SENDER_ID'")
}

// map external sender ID to PD partner ID
def senderPartnerId = service.getPartnerId(senderAgency, senderScheme, senderId);
if (senderPartnerId == null){
throw new IllegalStateException("Sender partner ID not found for agency '"+senderAgency+"', scheme '"+senderScheme+"', and alternative id '"+senderId+"'")
}

// Partner Authorization: compare the two sender partner IDs!
if (!senderPartnerId .equals(senderPid)){
throw new IllegalStateException("User '"+user+"' is not authorized to send messages with ID '"+senderId+"'");
}


//receiverId is the external receiver ID used by the sender partner
def receiverId = properties.get("RECEIVER_ID");
if (receiverId == null){
throw new IllegalStateException("Receiver ID is not set in the property 'RECEIVER_ID'")
}

// map the external receiver ID of the sender to PD partner ID
def receiverPid = service.getPartnerId(senderAgency, senderScheme, receiverId);
if (receiverPid == null){
throw new IllegalStateException("Receiver partner ID not found for agency '"+senderId+"', scheme '"+senderScheme+"', and alternative id '"+receiverId+"'")
}
// set "RECEIVER_PID" property
message.setProperty("RECEIVER_PID", receiverPid);


// RECEIVER_ADDRESS determination
def parameterValue = service.getParameter("ADDRESS", receiverPid , String.class);
if (parameterValue == null){
throw new IllegalStateException("ADDRESS parameter not found in the Partner Directory for the partner ID "+receiverPartnerId );
}
message.setProperty("RECEIVER_ADDRESS", parameterValue );

// get agency and scheme of receiver
def receiverAgency = service.getParameter("AGENCY", receiverPid, String.class);
if (receiverAgency == null){
throw new IllegalStateException("AGENCY parameter not found in the Partner Directory for the partner ID "+receiverPid);
}
def receiverScheme = service.getParameter("SCHEME", receiverPid, String.class);
if (receiverScheme == null){
throw new IllegalStateException("SCHEME parameter not found in the Partner Directory for the partner ID "+receiverPid);
}

// map the internal receiver ID to the external format of the receiver
def externalReceiverId = service.getAlternativePartnerId(receiverAgency , receiverScheme , receiverPid);
if (externalReceiverId == null){
throw new IllegalStateException("Receiver partner ID not found for agency '"+receiverAgency +"', scheme '"+receiverScheme +"', and partner Id '"+receiverPid+"'")
}
// set "EXTERNAL_RECEIVER_ID" property used by the receiver
message.setProperty("EXTERNAL_RECEIVER_ID", externalReceiverId);

// map the internal sender ID to the external format of the receiver
def externalSenderId = service.getAlternativePartnerId(receiverAgency , receiverScheme , senderPid);
if (externalSenderId == null){
throw new IllegalStateException("Sender partner ID not found for agency '"+receiverAgency +"', scheme '"+receiverScheme +"', and partner Id '"+senderPid+"'")
}
// set "EXTERNAL_SENDER_ID" property
message.setProperty("EXTERNAL_SENDER_ID", externalSenderId);

// header for dynamic receiver XSLT selection
message.setHeader("RECEIVER_XSLT","pd:"+receiverPid+":RECEIVER_XSLT:Binary");

return message;
}

Groovy Script 3: "Script"

The Groovy script

  • reads the sender PD partner ID from the property “SENDER_PID”,

  • determines the sender dependent agency and scheme from the Partner Directory,

  • reads the agency ID of the sender from the property “SENDER_ID”,

  • maps this agency ID to the corresponding PD partner ID with help of the Alternative Partner entries in the Partner Directory,

  • compares the mapped value with the read value from the property “SENDER_PID” (Partner Authorization) to ensure that a partner can only sent sender ID values in the payload which correspond to the configured logged-in user,

  • reads the agency ID of the receiver from the property “RECEIVER_ID”,

  • maps this receiver ID to the corresponding PD partner ID with help of the Alternative Partner entries in the Partner Directory,

  • determines for the receiver PD partner ID the receiver address from the Partner Directory,

  • sets the receiver address to the property “RECEIVER_ADDRESS”,

  • determines the agency and scheme of the receiver using the receiver PD partner ID,

  • maps the sender and receiver PD partner ID to the IDs of the receiver agency with help of the Alternative Partner entries in the Partner Directory for the receiver PD partner ID,

  • stores the mapped IDs into the properties “EXTERNAL_SENDER_ID” and “EXTERNAL_RECEIVER_ID”,

  • sets the Partner Directory URI for the receiver XSL transformation to the header “RECEIVER_XSLT”.


The header “RECEIVER_XSLT” and the properties “EXTERNAL_SENDER_ID” and “EXTERNAL_RECEIVER_ID” are consumed by the following XSLT mapping step.

Step 6: Receiver XSL Transformation


Create an XSLT Mapping step with the name “Receiver XSL Transformation”. In the “Processing” tab select for the “Source” field the option “Header” and enter in the “Header Name” field the value “RECEIVER_XSLT” as shown in the following screen shot.



Screen Shot 2: Processing Properties of the “Receiver XSL Transformation” Step

The “Receiver XSL Transformation” step is reading dynamically from the header “RECEIVER_XSLT” the Partner Directory URI of the receiver partner dependent XSL transformation.

The receiver XSL transformation transforms the intermediate XML structure to the receiver XML structure using the properties “EXTERNAL_SENDER_ID” and “EXTERNAL_RECEIVER_ID” containing the receiver agency ID values for the sender and receiver. See previous chapter “XML Structure Transformation – Code Mapping – Partner Directory URI”.

Step 7: Remove Headers


Create a Content Modifier step which deletes the headers

SapAuthenticatedUserName”, “RECEIVER_XSLT”, “SENDER_XSD”, and “SENDER_XSLT

(The header “SapAuthenticatedUserName” was introduced in the previous blog). See the following screen shot.



Screen Shot 3: Content Modifier "Remove Headers"

The headers must be removed before the SOAP receiver channel is invoked, otherwise the headers would be transferred as HTTP headers to the receiver.

Note, that exchange properties are not transferred to the receiver in a receiver SOAP or HTTP channel. We recommend, therefore, to use properties instead of headers whenever possible.

Creating Partner Directory Entries


Before you can call the integration flow you must also fill the Partner Directory with additional String Parameter, Binary Parameter, and Alternative Partner entries.

String Parameters


In the sub-chapter “Step 3.1 Creating/Updating/Deleting a String Parameter Entry” of the blog https://blogs.sap.com/2017/07/25/cloud-integration-partner-directory-step-by-step-example/ we described how you can create/update/delete String Parameters.

There we have already created the following two String Parameter entries.



















Pid Id Value
Receiver_1 ADDRESS https://<receiver_iflmap>/cxf/receiver_1
Receiver_2 ADDRESS https://<receiver_iflmap>/cxf/receiver_2


Table 5: String Parameter Entries for the Receiver Address

Beside the String Parameters created in this previous blog, we need further 8 String Parameters as discussed in the previous chapter “Mapping of Agency Partner IDs to PD Partner IDs”.

You can use for the POST OData calls the following request bodies.
{"Pid":"Sender_BASIC","Id":"AGENCY","Value":"AgencyXYZ"}
{"Pid":"Sender_BASIC","Id":"SCHEME","Value":"LONG"}
{"Pid":"Sender_OAUTH","Id":"AGENCY","Value":"Sender_OAUTH_Agency"}
{"Pid":"Sender_OAUTH","Id":"SCHEME","Value":"Sender_OAUTH_Scheme"}
{"Pid":"Receiver_1","Id":"AGENCY","Value":"AgencyXYZ"}
{"Pid":"Receiver_1","Id":"SCHEME","Value":"LONG"}
{"Pid":"Receiver_2","Id":"AGENCY","Value":"AgencyXYZ"}
{"Pid":"Receiver_2","Id":"SCHEME","Value":"LONG"}

OData Request Bodies for Creating String Parameter Entries

Alternative Partners


How you can create/update/delete Alternative Partner entries is described in https://help.sap.com/viewer/368c481cd6954bdfa5d0435479fd4eaf/Cloud/en-US/a5c2c40db48e4f44b97f2687d6c... .

For the example scenario we need Alternative Partner entries which are described by the following request bodies.
{"Hexagency":"12", "Hexscheme":"12", "Hexid":"12", "Agency":"AgencyXYZ", "Scheme":"LONG","Id":"Receiver Premium","Pid":"Receiver_1"}
{"Hexagency":"12", "Hexscheme":"12", "Hexid":"12", "Agency":"AgencyXYZ", "Scheme":"LONG","Id":"Receiver 2","Pid":"Receiver_2"}
{"Hexagency":"12", "Hexscheme":"12", "Hexid":"12", "Agency":"AgencyXYZ", "Scheme":"LONG","Id":"Main Sender","Pid":"Sender_BASIC"}
{"Hexagency":"12", "Hexscheme":"12", "Hexid":"12", "Agency":"AgencyXYZ", "Scheme":"LONG","Id":"Sender Company XYZ","Pid":"Sender_OAUTH"}
{"Hexagency":"12", "Hexscheme":"12", "Hexid":"12", "Agency":"Sender_OAUTH_Agency", "Scheme":"Sender_OAUTH_Scheme","Id":"Receiver Premium","Pid":"Receiver_2"}
{"Hexagency":"12", "Hexscheme":"12", "Hexid":"12", "Agency":"Sender_OAUTH_Agency", "Scheme":"Sender_OAUTH_Scheme","Id":"Receiver 1","Pid":"Receiver_1"}
{"Hexagency":"12", "Hexscheme":"12", "Hexid":"12", "Agency":"Sender_OAUTH_Agency", "Scheme":"Sender_OAUTH_Scheme","Id":"self","Pid":"Sender_OAUTH"}

OData Request Bodies for Creating Alternative Partner Entries

Remark: the properties "Hexagency", "Hexscheme", "Hexid" contain dummy values. See https://help.sap.com/viewer/368c481cd6954bdfa5d0435479fd4eaf/Cloud/en-US/a5c2c40db48e4f44b97f2687d6c....

Binary Parameters


The XSL XSD and XML documents discussed in chapters “XML Structure Transformation – Code Mapping – Partner Directory URI” and “XSD Documents” must be entered as Binary Parameters into the Partner Directory. Binary Parameters can be created/changed/deleted in a similar way as String Parameters. Instead of the request URI “https://<tmn>api/v1/StringParameters” you use the URI

“https://<tmn>api/v1/BinaryParameters”.

See also https://help.sap.com/viewer/368c481cd6954bdfa5d0435479fd4eaf/Cloud/en-US/47b69992cd944e93903d46d700e...

Beside the fields “Pid”, “ID”, “Value”, the Binary Parameters have the field “ContentType”. Possible values for “ContentType” are “xml”, “xsl”, “xsd”, “json”, “text”, “zip”, “gz” (for GZIP files), “zlib”, “crt” (for DER encoded X.509 certificate).

The “Value” field contains binary content. The maximum length of the “Value” field is restricted to 260 KB.

We recommend to store the XSL, XML, and XSD documents used in the XML Validator and the XSLT Mapping step in zip format (ContentType = “zip”). The XML Validator and XSLT Mapping step automatically will unzip documents with Content Type “zip”. The zip compression allows you to store XSLT, XSD, XML documents which are uncompressed bigger than 260 KB as Binary Parameters in the Partner Directory.

If you use Postman to make OData calls then you must base64 encode the zipped documents. We have already prepared the zipped and base 64 encoded documents for you which we introduced in the chapter “XML Structure Transformation – Code Mapping – Partner Directory URI” and “XSD Documents”. See the following OData request body samples.
{"Pid":"Sender_BASIC","Id":"SENDER_XSLT","ContentType":"zip","Value":"UEsDBBQAAAAIAOlpEEvcQmtFyQEAACAFAAAQAAAAc2VuZGVyX2Jhc2ljLnhzbMWUW2vbMBTHn1PodxB6d7RuL4uxXWiajcI2RtKOvRkhn8QC3ZCO4+TbT7aT5tILHWVM+MESv//5n3N0ya43WpE1+CCtyenV+AMlYIStpFnl9OH+S/KZXheXF9kmqDTgVkGoAfCg+BgVlxckjhjIhDRyOa0RXcpY27bj9tPY+hW7mkwm7PfiG7v33ISl9fpEVQv5qArcjYXVTCKLzGgANJdmIEJEulnP7ILARqimgsRDaBQmzsNSbiBEgZA0Zk8GrC9Camc9kjoyOXVV+hUMeCl+co/xp8u/bFCq9EYa7reUncltg65BogFrW+U0Zve0YUSaCgzm1FhKzgMgaKc4AtEcRZ1T1ie4G9l3CIGvIC6NRqOe586pbbJXBVZ03JGCHSTD/NikixO/Z40XELP0tEMGQHClHo2I4RpyGgBL560Dj1t6lFUrsU4c91zvwD1UdlNaLGY/bmfz8u42Y6f4m2KsuWqAkgAKRGzjuN+FqGJP0nyl6hc7PgcBcv3PSp/PprO7X/+5+Oe3vLs36Y2thnp67dQajGe16PneOrHLE/OM7Zm/tZs23se7ceT2Uq9x/yqUYqcp45WCV9se+vN7Jnhn24a1wztX/AFQSwECHwAUAAAACADpaRBL3EJrRckBAAAgBQAAEAAkAAAAAAAAACAAAAAAAAAAc2VuZGVyX2Jhc2ljLnhzbAoAIAAAAAAAAQAYAM9Dm/GAFtMBfn7PHpgV0wFsY8kemBXTAVBLBQYAAAAAAQABAGIAAAD3AQAAAAA="}

OData Request Body for Creating Binary Parameter of "Sender XSL Transformation for Sender_BASIC"
{"Pid":"Sender_OAUTH","Id":"SENDER_XSLT","ContentType":"zip","Value":"UEsDBBQAAAAIAFVrEEsDFZ9/ywEAADYFAAAQAAAAc2VuZGVyX29hdXRoLnhzbMWUXWvbMBSGr1PofxC6d7RuN4uxXVibjcA2RtKO3hkhn8QCWRLScT7+/WTZaT66hrIxJnxhHZ73nPccy8put40ia3BeGp3Tm/E7SkALU0m9yunjw+fkI70trq+yrVepx50CXwPgQfE+KK6vSFghkfZp4HJaI9qUsc1mM958GBu3YjeTyYQ9Lb6yB8e1XxrXnKhqIZ9VntuxMA2TyAIz6gEPatkTvkPCLjJDEtgK1VaQOPCtwsQ6WMot+CAQkgb3pMdiE7KxxiGpA5NTW6VfQIOT4gd3GF46/2WLUqWfpOZuR9mZ3LRoWyQNYG2qnAZ3LwdGpK5AY061oeQ8AUJjFUcgDUdR55RFg8PKvoH3fAUhNBqNIs+tVbtkr/Ks6LgjBTtI+v1xkS5PeH5buBtiuoBg1c0q2pE9J7hSz/WI5g10LJbWGQsOd/TI3EZinVjueDOAe6jstrRYTL/fT+fl7D5jp/ibcqy5aoGSYBREmOY4foygYi9sXmg+xl/tfw4C5PofTmA+vZvOfv7nGVw4AHdGYzirsaUoHwJFlMTqiVme1M/Ynvmziq1z4Y/ZHUq+NnPc3xWlGDRl+NHg4vh9PNBngr8cXx873H7FL1BLAQIfABQAAAAIAFVrEEsDFZ9/ywEAADYFAAAQACQAAAAAAAAAIAAAAAAAAABzZW5kZXJfb2F1dGgueHNsCgAgAAAAAAABABgAo8+biYIW0wGN1jtIxBXTAbRFNUjEFdMBUEsFBgAAAAABAAEAYgAAAPkBAAAAAA=="}

OData Request Body for Creating Binary Parameter of "Sender XSL Transformation for Sender_OAUTH"
{"Pid":"GenericPartner","Id":"xsl_util","ContentType":"zip","Value":"UEsDBBQAAAAIAJlpEEvRr/FglgEAAGEDAAAMAAAAeHNsX3V0aWwueHNsdZNdS8MwFIavK/gfQhio4BY/blxZJyjqjRfiBwgiI6ZnWzBNwkm6rf/e9Gtb3daL0rTPe97z5qSj21WmyALQSaMTejm4oAS0MKnUs4R+vD/2b+jt+PhotHIqdr5Q4OYAfqO4CorjIxKuUEi7OHAJnXtvY8aWy+VgeT0wOGOXw+GQfb49s3fk2k0NZh3VXMi1ynE7ECZj0rPARDWQcalrwgWkXFVMUwRWQuUp9BFcrnzfIkzlClwQCEnHNVPfqxyWI8+I5hkkNEjnXM+AssBFW9CCo+Q/ChruPkcMG1PcmxQcJQ4UCJ/Q1Ig8A+1PT2waP4EGlOKFow8PcUcS30nNsTg5a42iysVDZhX3rYtvd2ciGvEkzALKDBHZ278DnQL+w0nlEZFR28K4iaRy6Jvpuvtep0X2bMzvh2UP2mPx9VYVLj8kvX0m3+wVBMhFzYRUI7Z2K9Ox7XjVDA5kduAnFo0F9MU66E7OlpiUyzbgYaqK2sF2woezEQfvl0Zy2muPwjnpddy211WVZoY7EcNU63ebH2X8B1BLAQIfABQAAAAIAJlpEEvRr/FglgEAAGEDAAAMACQAAAAAAAAAIAAAAAAAAAB4c2xfdXRpbC54c2wKACAAAAAAAAEAGAAVgvuYgBbTAa11N2KAFtMBrXU3YoAW0wFQSwUGAAAAAAEAAQBeAAAAwAEAAAAA"}

OData Request Body for Creating Binary Parameter of XSL Transformation "xsl_util"
{"Pid":"GenericPartner","Id":"CurrencyCodes","ContentType":"zip","Value":"UEsDBBQAAAAIANxhEEvnaVbfeAAAAPAAAAARAAAAQ3VycmVuY3lDb2Rlcy54bWyzsa/IzVEoSy0qzszPU7BVUDLUM1BSSM1Lzk/JzEsHCYSGuOlaKNnb8XLZ+OTnZ4cWAFmcNq55JUWVIBanTXBqXkpqkXN+Sqqdio0+Eg8sG5SanJpZBhUJDXax0UcRAZmlDzcMh7GPmtYQMNg1NMgfn8k2+lC3AwBQSwECHwAUAAAACADcYRBL52lW33gAAADwAAAAEQAkAAAAAAAAACAAAAAAAAAAQ3VycmVuY3lDb2Rlcy54bWwKACAAAAAAAAEAGADDy4iCeBbTATVsflZ4FtMBfCl4VngW0wFQSwUGAAAAAAEAAQBjAAAApwAAAAAA"}

OData Request Body for Creating Binary Parameter for Currency Codes XML
{"Pid":"Receiver_1","Id":"RECEIVER_XSLT","ContentType":"zip","Value":"UEsDBBQAAAAIAOdZEEsamx96hwEAAJwDAAAOAAAAcmVjZWl2ZXJfMS54c2yVU8lOwzAQPadS/2GwuKZmudAqCYI2SJUQh7QgbsgkQxMpsS17uuTvcRPasoXFJ3s0b95iO7jcVCWs0NhCyZCdDk4YoExVVshFyO7nN/4Fu4z6vWBjy5GlukSbI9IBceYQ/R645QZJO3J9IcuJ9Ijz9Xo9WJ8PlFnw0+FwyB9nt3xuhLQvylTMTYV+z2sma2FEBVJUGLL4cR4nd1e3T7P4bhInT9MJ4xEER74PuElzIRcI2iiNhmpIlSRRSKcWKEewKDM0MJ24HcFz3RZTU2gCS6jB96NWbTdtEo/j6cM/iQ2mWKx+p/Ya03sBakl6SVAh5SoLmYvwa/xQOE+SQiYVAx59HEBY6VIQQiUozUPG2Zu/pmOi0i2n1xxm0yxqMCtRLtFXL05oiakbfPxt5AHfIrZwL0j+gP2YW8CTFr0Xs4ULrcva34m2Ll633gnmreJ2/95fG523ey+fbY/dbbiM2I4wuFZZ3aF40KhrGrqZOgMeL41xN1QfqHaVH+n2Td2Ube3wx6JXUEsBAh8AFAAAAAgA51kQSxqbH3qHAQAAnAMAAA4AJAAAAAAAAAAgAAAAAAAAAHJlY2VpdmVyXzEueHNsCgAgAAAAAAABABgA0soSLHAW0wHC4IxLoBXTAR0No0qgFdMBUEsFBgAAAAABAAEAYAAAALMBAAAAAA=="}

OData Request Body for Creating Binary Parameter of “Receiver XSL Transformation for Receiver_1”
{"Pid":"Receiver_2","Id":"RECEIVER_XSLT","ContentType":"zip","Value":"UEsDBBQAAAAIAPhZEEvjEwu4iAEAAKEDAAAOAAAAcmVjZWl2ZXJfMi54c2yVU0lPg0AUPtOk/+E58UrH5WIboFGLSRP1QKvxZkZ4FhKYmcy8Lvx7p2Bbl9ZlTvDyvnUgGK6qEhZobKFkyE57JwxQpior5CxkD9Mb/4INo24nWNlyYKku0eaItEOcOUS3A+44ImkHbi9kOZEecL5cLnvL854yM37a7/f50+SWT42Q9lWZijlW6Ha8hlkLIyqQosKQxU/TOLm/vH2exPejOHkejxiPIDjyfcBVmgs5Q9BGaTRUQ6okiUI6t0A5gkWZoYHxyD0RvNTtMDWFJrCEGnw/at0elk3i63j8+E9hgykWi9+lvSb01oCak54TVEi5ykLmKvxePxQuk6SQScWAR58JCCtdCkKoBKV5yDh7z9ds3KG1YoZrXa8ZTMZZ1OAWopyjr16d2RJTR368t/aArxFruBckf8B+7i7gSYveGlrDhdZl7W+MW1exOx9M853r9v1jzrZCb/PdfI1/7W7FdcU2osGVyuoDrnuNw2bhB6X9MnNj3DXVO53N5Eet7dJhvXa2+9GiN1BLAQIfABQAAAAIAPhZEEvjEwu4iAEAAKEDAAAOACQAAAAAAAAAIAAAAAAAAAByZWNlaXZlcl8yLnhzbAoAIAAAAAAAAQAYAAVdpD9wFtMBqlHeusMV0wH90ti6wxXTAVBLBQYAAAAAAQABAGAAAAC0AQAAAAA="}

OData Request Body for Creating Binary Parameter of “Receiver XSL Transformation for Receiver_2”
{"Pid":"Sender_BASIC","Id":"SENDER_XSD","ContentType":"zip","Value":"UEsDBBQAAAAIALtSEEt7o7kcTAEAAFgDAAAQAAAAc2VuZGVyX2Jhc2ljLnhzZJWSTU7DMBCF9z2FNWJL3MIGRUkqWoSEVDa0SOwq4wytpdgOdtI0W87DqTgJjlOpP+kPZGf7ezNvXiYarmVGVmis0CqGQdAHgorrVKhFDK+zx+s7GCa9yPIlSkYcrGwMy6LIQ0qrqgqq20CbBb3p9wf07Xky9Ry0YCiZUC1tHd6cAq4lhaRH3BcJmWtTEMUk2pxxPIaStvNEc1Z4i3kaTlGlaOaj++nTOOTa4Hxt03AkFDM1EJr02vKYoUTV1o/hQfOyOW6ae8J1yDNcz+oct7f+xeJn6XI4uD5StvUCpHA1YrCFccF5Dxd0L8hRrP6nNPgRQxNNONJp/Zcu49IYN0YNXdLTVjQBdOffgww25ngTP3lndmv2tMbrULnAjf9tZMWy0gmvjpq+pPr5+j6ri+iOxROT0nOjRnQT28EW0O4aRLSzNDtqp/DrmvwCUEsBAh8AFAAAAAgAu1IQS3ujuRxMAQAAWAMAABAAJAAAAAAAAAAgAAAAAAAAAHNlbmRlcl9iYXNpYy54c2QKACAAAAAAAAEAGACIOQS4aBbTAVzDbRpfFtMBXMNtGl8W0wFQSwUGAAAAAAEAAQBiAAAAegEAAAAA"}

OData Request Body for Creating Binary Parameter of XSD Document for sender “Sender_BASIC”
{"Pid":"Sender_BASIC","Id":"core_xsd","ContentType":"zip","Value":"UEsDBBQAAAAIAGBGEEt/HnAamgAAAMsAAAAVAAAAc2VuZGVyX2Jhc2ljX2NvcmUueHNkbY6xCsIwFEX3fkV4u3mtLlKaFhyc1EUF15A+2kLzUpJg7N8b7Op24d57OE33sbN4kw+TYwWVLEEQG9dPPCh4Ps67I3Rt0QQzktUijzkoGGNcasSUkkwH6fyA+7Ks8HW93H87EFH7geJNWwqLNrRdQv5YPbE0ziJssDpy+Nu2hWhoJkscBWeOgpPr10xel5xD9NkQMKvh5tZ+AVBLAQIfABQAAAAIAGBGEEt/HnAamgAAAMsAAAAVACQAAAAAAAAAIAAAAAAAAABzZW5kZXJfYmFzaWNfY29yZS54c2QKACAAAAAAAAEAGAB4WUcFXBbTAWIRbhpfFtMBYhFuGl8W0wFQSwUGAAAAAAEAAQBnAAAAzQAAAAAA"}

OData Request Body for Creating Binary Parameter of XSD Document "core_xsd”
{"Pid":"Sender_OAUTH","Id":"SENDER_XSD","ContentType":"zip","Value":"UEsDBBQAAAAIANVSEEuWYxKrNAEAADIDAAAQAAAAc2VuZGVyX29hdXRoLnhzZJ2SS07DMBCG9zmFZbElbmGDkNMuQJWQKAtaJLYmmaaW/EhtJ2m3nIdTcRKmplIf6UPq7Dzzf+N/RsOHS61IA85LazLaT3uUgMltIU2Z0Y/p6PaBDgcJ9/kctCAoNj6j8xCqR8batk3b+9S6kt31en32OX6dRB0lQbgSwpvQ4CuRwz/ikfGgZmluNaMJwQAFGkwYWaefYSZqFTK6qIWSMwkFHSRRxDcqYrBfRsfgvSgBq2QTHBtWCpbTVQXbbKx4WNQ40EH6SNcJmALcS4HesUtGfXC4A0rYRfIdcpDNdeyTNQFfV4C1czjXinaVUe3leiPdheyJHKw/zIO0hnwJvzVwmokcmFqDE5FrhKoRvDlq+hL1+/1zluNsx+KJSdm5UTnbrO3gLFj3LjjrXNEOjUQ87cEfUEsBAh8AFAAAAAgA1VIQS5ZjEqs0AQAAMgMAABAAJAAAAAAAAAAgAAAAAAAAAHNlbmRlcl9vYXV0aC54c2QKACAAAAAAAAEAGADPtj/VaBbTATRfbhpfFtMBNF9uGl8W0wFQSwUGAAAAAAEAAQBiAAAAYgEAAAAA"}

OData Request Body for Creating Binary Parameter of XSD Document for sender “Sender_OAUTH”

 

Normally you do not use Postman for making the OData calls. We recommend to use in your application an OData 2 client library like Olingo. See for example https://olingo.apache.org/doc/odata2/tutorials/OlingoV2BasicClientSample.html . With such a library it is not necessary to make the base 64 encoding for binary data; the library will do this automatically for you.

Preparation of the Receiver Iflows


We also enhance the receiver iflows so that the incoming XML document is validated against an XML schema.



Receiver Integration Flow with XML Validator

In each receiver integration flow, remove the Content Modifier and add a XML Validator step with one of the following XSD documents.
<?xml version="1.0" encoding="UTF-8"?>
<schema xmlns="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified">

<element name="Doc">
<complexType>
<sequence>
<element name="SId" type="string" />
<element name="RId" type="string" />
<element name="Body" type="string" />
<element name="Currency">
<simpleType>
<restriction base="string">
<enumeration value="USD" />
<enumeration value="EURO" />
</restriction>
</simpleType>
</element>
</sequence>
</complexType>
</element>
</schema>

XSD Document for Receiver “Receiver_1”
<?xml version="1.0" encoding="UTF-8"?>
<schema xmlns="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified">

<element name="Message">
<complexType>
<sequence>
<element name="SId" type="string" />
<element name="RId" type="string" />
<element name="Body" type="string" />
<element name="Currency">
<simpleType>
<restriction base="string">
<enumeration value="USD" />
<enumeration value="EURO" />
</restriction>
</simpleType>
</element>
</sequence>
</complexType>
</element>
</schema>

XSD Document for Receiver “Receiver_2”

Execution


Now we are ready to perform calls to our enhanced Partner Directory Integration Flow via Postman.

As explained in chapter  “Step 5: Call the Integration Flow” of Cloud Integration - Partner Directory - Step-by-Step Example you can make a HTTP call with BASIC authentication for the sender “Sender_BASIC”. The following documents contain the request and the expected response bodies for the sender “Sender_BASIC”.
<Document>
<Sender>Main Sender</Sender>
<Receiver>Receiver Premium</Receiver>
<Body xmlns="https://main.com/">test</Body>
<Currency>€</Currency>
</Document>

Request Body of Sender “Sender_BASIC” for Receiver “Receiver_1”
<Doc xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<SId>Main Sender</SId>
<RId>Receiver Premium</RId>
<Body>test</Body>
<Currency>EURO</Currency>
</Doc>

Response Body of “Receiver_1” to Sender “Sender_BASIC”
<Document>
<Sender>Main Sender</Sender>
<Receiver>Receiver 2</Receiver>
<Body xmlns="https://main.com/">test</Body>
<Currency>$</Currency>
</Document>

Request Body of Sender “Sender_BASIC” for Receiver “Receiver_2”
<Message xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<SId>Main Sender</SId>
<RId>Receiver 2</RId>
<Body>test</Body>
<Currency>USD</Currency>
</Message>

Response Body of Receiver “Receiver_2” to Sender “Sender_BASIC”

 

As explained in the chapter “Step 6.3 Calling the Partner Directory Integration Flow with OAuth Sender” of Cloud Integration - Partner Directory - Step-by-Step Example you can make a HTTP call with OAUTH authentication for the sender “Sender_OAUTH” with Postman. The following documents contain the request and the expected response bodies for the sender “Sender_OAUTH”.
<Message xmlns="https://self.com/">
<SenderId>self</SenderId>
<ReceiverId>Receiver 1</ReceiverId>
<Content>test</Content>
<Currency>$</Currency>
</Message>

Request Body of Sender “Sender_OAUTH” for Receiver “Receiver_1”
<Doc xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<SId>Sender Company XYZ</SId>
<RId>Receiver Premium</RId>
<Body>test</Body>
<Currency>USD</Currency>
</Doc>>

Response Body of “Receiver_1” to Sender “Sender_OAUTH”
<Message xmlns="https://self.com/">
<SenderId>self</SenderId>
<ReceiverId>Receiver Premium</ReceiverId>
<Content>test</Content>
<Currency>€</Currency>
</Message>

Request Body of Sender “Sender_OAUTH” for Receiver “Receiver_2”
<Message xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<SId>Sender Company XYZ</SId>
<RId>Receiver 2</RId>
<Body>test</Body>
<Currency>EURO</Currency>
</Message>

Response Body of Receiver “Receiver_2” to Sender “Sender_OAUTH”

Exercise: Mapping the Response to Sender XML Structure and IDs


The senders get response documents which have the XML structure of the receivers and which have the IDs of the receiver agencies. In a real productive scenario the response documents must be mapped back to the sender XML structure and the IDs of the sender agency. We leave this task as exercise for the reader.

Hint: Call the receivers in an “External Call” with a “Request Reply” step and add after the “Request Reply” step further steps which determine in a script the Partner Directory URIs for the two additional XSLT Mapping steps making the transformation from the receiver structure to the intermediate structure and from the intermediate structure to the sender structure. Use also the already set properties

  • SENDER_PID

  • RECEIVER_PID

  • SENDER_ID

  • RECEIVER_ID


 
2 Comments