Map custom payloads
Overview
This documentation provides a walkthrough of how to map and deliver custom payloads in API integrations. The focus is on mapping a raw JSON payload to a target API endpoint, and handling the responses.
Example Payload
The following is a sample payload:
{
"elementType": "person",
"code": "4637115",
"dateOfBirth": "1985-01-01"
},
{
"elementType": "person",
"code": "4637999",
"dateOfBirth": "1986-01-01"
}
Service Definition
The schema definition is required for the target definition. Create a DOH service definition as follows:

The root element name cam be changed to anything.
The payload attribute can specify a default source PAYLOAD column name that will contain the actual payload to be used in the request. This is just the default and can be overridden in the target mapping.
The URL should point to the API endpoint and will then be appended to the serverUrl from the task.
Table Definitions
To keep track of newly generated person IDs returned by the target application, you should create a table with the following columns:
CREATE TABLE CX_ABC_PERSON (
PERSON_ID VARCHAR2(30),
CX_PER VARCHAR2(30)
);
PERSON_ID— Stores the newly generated ID assigned by the API after a successful creation.CX_PER— Stores the original legacy ID, corresponding to the code field in the outbound payload.
This mapping allows you to link each new person ID from the API to its original reference in your source system.

Then, add the table definition to DOH. Make the PERSON_ID as the primary key, which is required for later steps.
Create the table
CREATE TABLE INPUT_ABC_PERSONS (
ELEMENT_TYPE VARCHAR2(30 BYTE),
PERSONCODE VARCHAR2(30 BYTE),
INITIALS VARCHAR2(20 BYTE),
FIRST_NAME VARCHAR2(30 BYTE),
NAME VARCHAR2(200 BYTE),
DATE_OF_BIRTH VARCHAR2(10 BYTE),
LANGUAGE VARCHAR2(10 BYTE),
DOBINTERPRETATION VARCHAR2(1 BYTE),
NAMEFORMAT VARCHAR2(30 BYTE),
EMAIL_ADDRESS VARCHAR2(60 BYTE),
PHONE_NUMBER_MOBILE VARCHAR2(30 BYTE),
GENDER VARCHAR2(1 BYTE),
TITLE VARCHAR2(30 BYTE),
START_DATE VARCHAR2(20 BYTE),
CONSTRAINT ABC PRIMARY KEY (PERSONCODE)
);
Add test data to the table
INSERT INTO DIHADM.INPUT_ABC_PERSONS (
ELEMENT_TYPE,
PERSONCODE,
INITIALS,
FIRST_NAME,
NAME,
DATE_OF_BIRTH,
LANGUAGE,
DOBINTERPRETATION,
NAMEFORMAT,
EMAIL_ADDRESS,
PHONE_NUMBER_MOBILE,
GENDER,
TITLE,
START_DATE
) VALUES (
'person',
'4637115',
'TS',
'Teddy',
'Bear',
'1985-01-01',
'en',
'E',
'PERSON_NAME_FORMAT',
'test3.testsur2@gmail.com',
'4564564563',
'M',
'MR',
'2024-10-01'
);
INSERT INTO DIHADM.INPUT_ABC_PERSONS (
ELEMENT_TYPE,
PERSONCODE,
INITIALS,
FIRST_NAME,
NAME,
DATE_OF_BIRTH,
LANGUAGE,
DOBINTERPRETATION,
NAMEFORMAT,
EMAIL_ADDRESS,
PHONE_NUMBER_MOBILE,
GENDER,
TITLE,
START_DATE
) VALUES (
'person',
'4637999',
'TS',
'Teddy9',
'Bear9',
'1986-01-01',
'en',
'E',
'PERSON_NAME_FORMAT',
'test4.testsur2@gmail.com',
'88888888',
'M',
'MRS',
'2024-10-01'
);
COMMIT;
Define the source
The target mapping needs a source for the full payload.

SELECT
1 AS PAYLOADID,
JSON_ARRAYAGG(
JSON_OBJECT(
'elementType' VALUE IOP.ELEMENT_TYPE,
'code' VALUE IOP.PERSONCODE,
'dateOfBirth' VALUE IOP.DATE_OF_BIRTH
)
) AS PAYLOAD
FROM INPUT_ABC_PERSONS IOP
GROUP BY 1;
Tick the Generate Columns on Save before saving to geneerate the columns for the source. After saving, edit the source to set the primary key and save again.
Target definition and mapping sequences
The Target uses two mapping sequences:

- The first mapping sequence sends the custom payload and updates the
CX_ABC_PERSONtable with the generatedPERSON_IDand legacyCX_PERSON_IDvalues. - The second mapping sequence uses the
CX_ABC_PERSONtable as its source to retrieve the generatedPERSON_IDvalues for the next API request.
The source can be a direct reference to the CX_ABC_PERSON table or a query that returns the same data.
Main payload submission
The first mapping sends the custom payload. Map the @payload field to the PAYLOAD column from the payload source. The contents of the PAYLOAD column is directly sent as the request body without performing any field mapping.

Use generated IDs
This mapping sequence makes a second POST request using the IDs generated by the first request. The source is the CX_ABC_PERSON table created earlier.
Use the generated PERSON_ID in the URL Path. For example, /{root!PERSON_ID}.

Since this request does not require a request body, set the @payload mapping to null.
The following requests will be sent:
- no request body
Content-Length: 0
This mapping also overrides the default response handler by mapping @responseHandler.

Task definition and Groovy handlers
def handleResponse(ServiceAPIResult result) {
CommonEnv.logInfo(result.toString())
Map<String, String> idMap = new LinkedHashMap<>()
def jsonSlurper = new groovy.json.JsonSlurper()
def jsonObj= jsonSlurper.parseText(result.getHttpResponse().getBody())
println("Responsehandler 1: " + jsonObj)
jsonObj.each {perNode ->
idMap.put(perNode.id, perNode.code)
}
return idMap;
}
def handleResponse2(ServiceAPIResult result) {
CommonEnv.logInfo(result.toString())
def jsonSlurper = new groovy.json.JsonSlurper()
def jsonObj= jsonSlurper.parseText(result.getHttpResponse().getBody())
println("Responsehandler 2: " + jsonObj)
return null
}
The handleResponse method is the default name. If this method is defined, it will be called after each API call. The ServiceAPIResult parameter is the object that contains the results of the call and provides the following getter methods:
| Method | Returns |
|---|---|
getTaskWorkEntry() |
ServiceWorkEntry, extends TaskWorkEntry |
getHttpResponse() |
GenericHttpResponse |
getHttpMethod() |
String |
getUrlPath() |
String |
The GenericHttpResponse contains the response body and headers. The code above shows how to get the body.
For more information on the TaskWorkEntry and GenericHttpResponse formats, see make a GET calls.