Skip to main content
Part of the partner integration guide.

Overview

An Extole to Partner integration forwards Extole program activity to a partner platform. Start from a maintained source when it includes the required controllers and webhooks. When the source contains only display metadata, add the controller-backed delivery yourself. Substitute the component name, endpoints, and tag namespace from the partner page throughout. Build a Partner Integration with the Management API covers the constraints and shared mechanics every build follows.

When You Would Build One

Do not add Partner to Extole business-event scaffolding to this install. A partner that orders gift cards, prepaid cards, points, or payouts uses the distinct reward fulfillment model.

Before You Start

Read the partner page first — it names the finished tree, the endpoints, and the tag namespace — and inspect any matching source before choosing the build path. Without a complete source, create the container from Create the Integration Campaign and Component Model, then add the controller-backed delivery described below.

Choose the Build Path

List the duplicatable sources whose name matches the partner exactly, accepting every integration-v10.* revision — Install the Maintained Source shows the query — then inspect the integration component and its children. The integration component’s integration-v10.* type tells you the version, not whether the source delivers anything. A complete maintained source has all of the following:
  • An integration component tagged internal:self-managed
  • Child controllers for the activity it forwards
  • Webhook actions with event-specific data
  • The webhooks and credential settings those actions reference
When the source carries only display metadata, use the controller-backed path below. Choose each controller’s trigger by the kind of activity it forwards: Share-link creation and shared are distinct. The first creates a shareable and exposes its link; the second records a share action. Forwarding a fulfilled reward to a messaging or analytics partner is not the same as a partner that supplies the reward. A gift card, prepaid card, points, or payout provider uses Build a Reward Fulfillment Integration.

How to Build

Confirm the Finished Shape

The partner page’s product description specifies the finished tree. Each statement it makes maps to something the install must carry: Read that mapping as exhaustive rather than as a minimum, and apply it to an integration already in the account as much as to a fresh install. A maintained source ships the union of what every account might want, so it commonly installs children the page does not list and only one of the webhooks it names. A maintained source may not ship the report-runner and event-stream views every integration carries. Read the installed views socket and add whichever is missing from Add the Activity and Event Views.

Create Controller-Backed Outbound Delivery

Skip this section when the maintained source already contains the requested controllers and payloads. Create one controller per event class or payload contract. Attach the controller to the integration component with component_ids; do not modify a marketing campaign to host integration behavior. Create a controller:
Record the returned controller identifier as CONTROLLER_ID. Refresh the campaign version, then add a step-event trigger:
For share-link creation, use the same endpoint with event_type set to SHAREABLE and read the link from context.causeEvent.shareable.link. Create every controller and trigger while the path is disabled. Then publish and create the component-scoped webhook, as described in Publish, Then Attach Component-Scoped Webhooks, and attach it to the controller through Attach the Webhook Action. Take field names and identity rules from the partner page.

Create Missing Component Types

A typed child needs its component type first, and a partner page can require a type the account has never used. Read the type, and create it only when the read finds nothing:
Omit parent. An empty types array leaves an untyped component, which satisfies no socket filter and no template lookup.

Install the Maintained Source

An install is POST /v1/components/{SOURCE_COMPONENT_ID}/duplicate without target_campaign_id: omitting the target campaign creates a new root integration campaign that copies the source tree, including its webhooks and child controllers. Send a body carrying at least one property, such as component_display_name. List the candidates before duplicating anything:
Choose the Extole-owned source.

Reshape the Install

The reshape uses these calls, each needing a campaign version read immediately beforehand: Bring the installed tree to the partner page’s shape in one pass:
  • Delete the installed children the partner page does not keep.
  • Create the children it adds, including any typed data template.
  • Remove parent settings that belonged to a deleted child, such as a trigger-event-name setting whose controller is gone.
  • Set one WEBHOOK_ID setting per partner endpoint, resolved by webhook tag rather than by identifier, so the setting survives a rebuild:
Filter on the purpose tag exactly one webhook carries — here internal:partner:message-trigger, matching the webhook below. Never use a shared tag such as internal:partner, which matches every webhook the integration owns. A partner data template is a typed child of the integration component, created through component_ids with no socket. Its install expression anchors the source component’s unanchored step data onto the target event:

Publish, Then Attach Component-Scoped Webhooks

Publish the campaign once before creating any webhook whose name or URL expression calls context.getComponent(), and create those webhooks with component_ids naming the integration component. The reshape cannot complete without that publish, so get any release approval first.
A published integration campaign has no supported route back to a draft: there is no stop or unpublish action, and archiving takes the integration out of use entirely.
Publishing validates every webhook the campaign already owns, so keep a valid placeholder host in any account-URL setting that feeds a webhook URL. The maintained source’s own default is one. Set enabled to false while a webhook points at that placeholder — enabled, it sends live program data to a host that should never receive it, unsigned when the client key is also missing. Enabling it is the step that puts the partner connection into service. POST /v6/webhooks:
Record the returned webhook identifier as WEBHOOK_ID. Name each webhook for the endpoint it calls: an ingestion endpoint and a message-trigger endpoint are separate webhooks with separate tags. Keep the broad internal:partner tag for listing every webhook the integration owns. Where the account URL setting may lack a scheme, build the URL expression to add https://.

Attach the Webhook Action

Refresh the campaign version after creating the webhook, then attach the action to its controller. Map the complete partner payload here rather than leaving a generic request body for later:
Keep the controller, action, and webhook disabled until the credential, request handler, payload mapping, and response handling are complete.

Complete the Request and Response Handlers

The default request handler serializes the webhook action’s data as a JSON body, uses the configured method and URL, and applies the client key’s default authentication. A PASSWORD key adds an Authorization: Bearer header. Write a custom request expression when the partner requires a distinct authentication header, body envelope, URL, method, or idempotency key. Build the request from the webhook action data and the client key, following the contract on the partner page. Do not use createRequestBuilderWithDefaults() when its default authentication differs from the partner’s requirement. The response handler returns:
  • OK when processing is complete
  • RETRY when Extole should use the configured retry intervals
Without a response handler, Extole retries non-2xx responses. Add one when the partner contract distinguishes retryable responses such as 429 or 5xx from terminal 4xx configuration or payload errors. Log the terminal status and the minimum response detail needed to diagnose the rejection; do not log credentials or the full participant payload. A webhook is ready when its request handler produces the partner’s required body and authentication and its response handler follows the partner’s retry contract. Keep it disabled until both are verified.

Attach the Credential

Create the webhook client key once you have the partner’s API secret, then set the credential setting on the integration component. A missing credential does not block the build: leave the setting null and track it as outstanding.

Error Handling

How to Test

A 2xx on the duplicate call means the source tree was copied, not that the install matches the partner page. Read the campaign and its /v6/webhooks entries back, then confirm:
  • The tree matches the partner page: one child per activity the page lists, and no child forwarding activity it does not.
  • Every typed child carries its type.
  • Every requested activity has the matching controller trigger: SHAREABLE, STEP, or a FULFILLED reward event.
  • Every controller has a webhook action with the complete partner payload.
  • Each webhook exists with its tags and its resolved URL.
  • Each WEBHOOK_ID setting resolves to a webhook identifier rather than null.
  • Request and response handlers match the partner’s authentication, body, success, and retry contracts.
  • enabled is true on every webhook whose real URL and credential are both configured, and false on the rest.
Trigger each Extole event the integration forwards and confirm the partner endpoint receives the expected payload. Enable only the paths whose destination and credential are ready.