Template specs for destinations created with Destination SDK
Use the template spec part of the destination server configuration to configure how to format the HTTP requests sent to your destination.
In a template spec you can define how to transform profile attribute fields between the XDM schema and the format that your platform supports.
Template specs are part of the destination server configuration for real-time (streaming) destinations.
To understand where this component fits into an integration created with Destination SDK, see the diagram in the configuration options documentation or see the guide on how to use Destination SDK to configure a streaming destination.
You can configure the template specs for your destination via the /authoring/destination-servers endpoint. See the following API reference pages for detailed API call examples where you can configure the components shown in this page.
Supported integration types supported-integration-types
Refer to the table below for details on which types of integrations support the functionality described on this page.
Configure a template spec configure-template-spec
Adobe uses a templating language similar to Jinja to transform the fields from the XDM schema into a format supported by your destination.
For more information about the transformation, visit the links below:
See below an example of an HTTP request template, together with descriptions of each individual parameter.
{
"httpTemplate":{
"httpMethod":"POST",
"requestBody":{
"templatingStrategy":"PEBBLE_V1",
"value":"{ \"attributes\": [ {% for ns in [\"external_id\", \"yourdestination_id\"] %} {% if input.profile.identityMap[ns] is not empty and first_namespace_encountered %} , {% endif %} {% set first_namespace_encountered = true %} {% for identity in input.profile.identityMap[ns]%} { \"{{ ns }}\": \"{{ identity.id }}\" {% if hasSegments(input.profile.segmentMembership) %} , \"AEPSegments\": { \"add\": [ {% for namespace in input.profile.segmentMembership %} {% for segment in input.profile.segmentMembership[namespace.key] %} {% if (segment.value.status == \"realized\" or segment.value.status == \"existing\") and destination.namespaceSegmentAliases[namespace.key][segment.key] is defined %} {% if added_segment_found %} , {% endif %} {% set added_segment_found = true %} \"{{ destination.namespaceSegmentAliases[namespace.key][segment.key] }}\" {% endif %} {% endfor %} {% endfor %} ], \"remove\": [ {% for namespace in input.profile.segmentMembership %} {% for segment in input.profile.segmentMembership[namespace.key] %} {% if segment.value.status == \"exited\" and destination.namespaceSegmentAliases[namespace.key][segment.key] is defined %} {% if removed_segment_found %} , {% endif %} {% set removed_segment_found = true %} \"{{ destination.namespaceSegmentAliases[namespace.key][segment.key] }}\" {% endif %} {% endfor %} {% endfor %} ] } {% set removed_segment_found = false %} {% set added_segment_found = false %} {% endif %} {% if input.profile.attributes is not empty %} , {% endif %} {% for attribute in input.profile.attributes %} \"{{ attribute.key }}\": {% if attribute.value is empty %} null {% else %} \"{{ attribute.value.value }}\" {% endif %} {% if not loop.last%} , {% endif %} {% endfor %} } {% if not loop.last %} , {% endif %} {% endfor %} {% endfor %} ] }"
},
"contentType":"application/json"
}
}
httpMethodGET, PUT, POST, DELETE, PATCH.templatingStrategyPEBBLE_V1.valueFor information on how to write the template, read the section on using templating.
For more information about character escaping, see the RFC JSON standard, section seven.
For an example of a simple transformation, see the profile attributes transformation.
contentTypeapplication/json.Convert a template to support external audiences template-converter-tool
Older templates only read audience membership from the ups namespace. Update these templates to iterate over every namespace in segmentMembership, so that they also read membership for external audiences.
For information on how to configure your destination to support external audiences, see Configure support for external audiences.
Use the Template Converter tool to convert your existing template automatically. The tool rewrites a template that reads only the ups namespace into a template that iterates over all namespaces in segmentMembership, including external audiences.
Download the Template Converter tool
The tool requires Java Runtime Environment (JRE) 11 or later. It supports two modes:
-
Command line interface (CLI) mode: Run the tool from a terminal and pass your existing template as a parameter.
code language-shell java -jar templates-converter-cli.jar "your-existing-template-string"The tool prints the converted template to the terminal.
-
User interface (UI) mode: Run the tool with a graphical interface. This mode requires the JavaFX SDK, which is included in the downloaded archive.
code language-shell java --module-path="./javafx-sdk-17.0.7/lib" --add-modules=javafx.controls,javafx.fxml -jar templates-converter-ui.jar
After you convert your template, test it against multiple sample profiles using the render template API to confirm that it still renders correctly before you add it to your destination server configuration.
Configure request headers headers
In addition to the request body, you can add custom HTTP headers to the calls Experience Platform makes to your destination. Each header entry uses the same templatingStrategy and value fields as other templatized fields in the destination server.
"httpTemplate": {
"httpMethod": "POST",
"headers": [
{
"header": "Authorization",
"value": {
"templatingStrategy": "PEBBLE_V1",
"value": "Basic {{ (authData.username + ':' + authData.password) | base64encode }}"
}
},
{
"header": "x-integration",
"value": {
"templatingStrategy": "PEBBLE_V1",
"value": "{{customerData.integrationId}}"
}
},
{
"header": "Amazon-Advertising-API-ClientId",
"value": {
"templatingStrategy": "PEBBLE_V1",
"value": "{{authData.clientId}}"
}
},
{
"header": "Accept",
"value": {
"templatingStrategy": "NONE",
"value": "application/json"
}
}
]
}
headerAuthorization, Content-Type, or a custom header.value.templatingStrategyPEBBLE_V1 when the header value is dynamic or uses Pebble expressions. Use NONE for static values.value.value{{customerData.integrationId}}, {{authData.clientId}}, or {{ (authData.username + ':' + authData.password) | base64encode }}.Some partner APIs require a custom header populated with a value from the authentication credentials that customers provide, rather than the standard Authorization header. The Amazon-Advertising-API-ClientId header shown above is an example of this pattern, where the header value comes directly from an authData field.
value is a flat string instead of an object with templatingStrategy and value fields. For an example, see audience metadata management.For destinations using Basic authentication that require a custom Base64-encoded header, see Customize the Basic authentication header.
Next steps next-steps
After reading this article, you should have a better understanding of what a template spec is, and how you can configure it.
To learn more about the other destination server components, see the following articles: