Event Forwarding to Third-Party Tools
Pulse can forward a selected subset of the events it already tracks to a third-party marketing tool, so you do not have to instrument the same user action twice. You keep pushing events to Pulse exactly as you do today; Pulse mirrors the ones you nominate into the other tool.
Forwarding is driven entirely by a remote setting. There is no client-side API, no config flag and no code change on your side — nothing is forwarded until that setting exists.
Today Pulse supports CleverTap only. If you need a different tool (Braze, Amplitude, Mixpanel, …), request it from the Pulse team — each destination needs its own integration in the SDK and cannot be configured remotely on its own.
How it works
- On startup, the tracker fetches the event-forwarding remote setting.
- If the setting nominates at least one event for a supported destination, Pulse starts the forwarder for that destination. If it nominates none, nothing starts and there is no runtime cost.
- The forwarder reads events from the
dataLayer. It first processes everything already in thedataLayer— events recorded while the setting request was still in flight are not lost — then watches for anything pushed afterwards. - For every event, Pulse looks up its name in the setting. Events not listed are ignored. Listed events are renamed, reshaped, and handed to the destination tool.
Pulse's own tracking always runs first. A problem on the forwarding side can never cost you a Pulse event.
Only events that reach the dataLayer are forwarded. Every built-in event (click, popup, session_start, …) and every event you push to the dataLayer qualifies. Events sent by calling the tracker API directly (for example pulse.event(...)) bypass the dataLayer and are therefore not forwarded.
Requesting the remote setting
Contact the Pulse team with:
- your application name;
- the destination tool (currently CleverTap);
- the list of Pulse events you want forwarded;
- for each event, the name it should appear under in the destination tool;
- for each event, the properties you want sent and the name each should carry.
The team creates the setting; forwarding begins on the next page load once it is live. No release on your side is required.
Configuration schema
The setting value is a JSON object keyed by Pulse event name. Inside each event, one key per destination tool. Inside that, the mapping:
{
"popup": {
"clevertap": {
"name": "Popup",
"props": {
"action": "action",
"component": "component",
"component_type": "component_type",
"popup_source.section": "section",
"click_source.element.id": "trigger_element_id"
}
}
},
"session_start": {
"clevertap": {
"name": "Session Start"
}
}
}
This structure keeps one event's routing in one place, so an event can later be sent to more than one tool by adding a sibling key next to clevertap.
Event key
The key is the Pulse event name, exactly as it appears in Pulse — popup, click, session_start, and so on. See Built-in Events for the built-in names.
An event that is not a key in this object is not forwarded anywhere.
name
The name the event is recorded under in the destination tool. Omit it and the Pulse event name is used unchanged.
props
A strict allow-list of properties to forward:
- the key is a path into the event payload;
- the value is the property name to use in the destination tool.
Anything not listed is dropped. Omit props entirely and the event arrives carrying only the default properties.
Nested values are addressed with a dot-path. Using the popup event as an example, whose payload looks like this:
{
"component": "offer",
"component_type": "popup",
"action": "open",
"popup_source": { "section": "editor", "group": "toolbar" },
"click_source": {
"section": "header",
"element": { "id": "open-offer", "class_list": ["btn", "btn-primary"] }
}
}
| Path | Resolves to |
|---|---|
action | "open" |
popup_source.section | "editor" |
click_source.element.id | "open-offer" |
click_source.element.class_list | dropped — arrays are not supported |
click_source.element | dropped — objects are not supported |
A path must resolve to a string, number, boolean or date. Objects, arrays, null, undefined and NaN are silently dropped, because destination tools accept only scalar event properties. Always target a leaf value — click_source.element will never be forwarded, click_source.element.id will.
Default properties
Every forwarded event automatically carries three properties, whether or not props is present:
| Property | Value |
|---|---|
user_id | The Pulse user id from the current state. Omitted while nobody is signed in. |
device_id | The Pulse device id. Always present. |
timestamp | When the event occurred, as a date. |
These are applied after your mapping, so a mapping cannot overwrite or rename them. Pointing a props entry at user_id has no effect — the real value always wins.
They exist so events can be reconciled with Pulse records on the destination side. user_id and device_id come from Pulse state, so a sign-in mid-session is picked up automatically on subsequent events.
CleverTap
Pulse does not initialize CleverTap
Loading and configuring the CleverTap Web SDK — the account id, the region, the clevertap.min.js script — remains your responsibility, exactly as it is today. Pulse does not load the SDK, does not set your account id, and does not read or change your CleverTap configuration.
What Pulse does is narrow: it makes sure the window.clevertap queue object exists, and pushes forwarded events into window.clevertap.event.
This works whether or not CleverTap has finished loading when the event is forwarded. Before the SDK loads, the queue is a plain array and events accumulate in it; the SDK drains that queue on startup. After it loads, events go straight through. Either way nothing is lost, provided CleverTap is eventually initialized on the page.
If CleverTap is never initialized on the page, forwarded events sit in the queue and are never delivered. Pulse cannot detect or report this — make sure your CleverTap integration is in place before requesting forwarding.
Event and property naming
CleverTap reserves specific field names for user profiles (Name, Identity, Email, Phone, Gender, DOB, …), but Pulse never writes profiles — only events. Event property names are free-form, so you can pick whatever names suit your CleverTap workspace.
One CleverTap convention worth knowing: the event named Charged is special and expects Amount and Items properties. Avoid mapping an unrelated Pulse event to the name Charged.
User identity
Pulse forwards events only. It does not call onUserLogin and does not write CleverTap user profiles, so forwarded events attach to whichever profile your own CleverTap integration has established. The user_id and device_id default properties are provided so you can reconcile events yourself.
Things to keep in mind
Only the full Web SDK forwards events. The Mini SDK does not support event forwarding.
High-volume events multiply. Some built-in events fire far more often than they appear to — popup, for instance, fires once per mutated element, for both open and close. Forwarding one of these unfiltered can generate substantially more traffic in the destination tool than expected. There is no per-event filtering in the schema (for example, "only when action is open"), so nominate high-volume events deliberately.
Forwarding is additive. Nothing about your existing Pulse tracking changes when forwarding is enabled — the same events, with the same payloads, continue to reach Pulse.