Interact SDK Integration Guide
This guide explains how to integrate Zeotap’s Interact SDK into your website using the Web SDK or directly.
Overview
The Interact SDK enables secure, real-time client-side data delivery based on server-side configuration from your Zeotap account. It facilitates routing user profile data to supported platforms (e.g., Google Ad Manager, Adobe Target).
Use the Interact SDK test page to verify your integration end-to-end — send identifiers, trigger interactions, and inspect the resolved profile data returned by the SDK.
Web SDK Already Integrated
If you already use Zeotap's Web SDK, enable Interact by setting the loadInteractScript option to true during initialization.
<!-- Zeotap JS SDK -->
<script type="text/javascript">
!function(e,t){
var n=t.createElement("script");
n.type="text/javascript", n.crossorigin="anonymous", n.async=!0;
n.src="https://content.zeotap.com/sdk/zeotap.min.js";
var s=t.getElementsByTagName("script")[0];
s.parentNode.insertBefore(n,s);
function o(e,t,n){
function s(t){e[t]=function(){e[n].push([t].concat(Array.prototype.slice.call(arguments,0)))}}
for(var o=0;o<t.length;o++)s(t[o])
}
var r=e.zeotap||{_q:[],_qcmp:[]};
o(r,["init","setEventProperties","setUserProperties","setPageProperties","setMetaProperties","setUserIdentities","unsetUserIdentites","setZI"],"_q");
o(r,["setConsent","addAskForConsentActionListener"],"_qcmp");
e.zeotap=r;
}(window,document);
</script>
<script type="text/javascript">
window.zeotap.init("<YOUR_WRITE_KEY>", {
loadInteractScript: true,
// ... other options
});
</script>
The Zeotap Interact SDK will reference the source mapping and API key associated with the Zeotap JS SDK tag. Only the mapped identifiers from the source will be used to look up the user's profile in Zeotap.
Without Web SDK
If you're not using the Web SDK, add the Interact SDK directly to the head of your HTML/website.
<script type="text/javascript">
!function(t,n){
var e=n.createElement("script");
e.type="text/javascript", e.crossorigin="anonymous", e.async=!0;
e.src="https://content.zeotap.com/sdk/interact.min.js";
var o=n.getElementsByTagName("script")[0];
o.parentNode.insertBefore(e,o);
var a=t.zeotapInteract||{_q:[]};
!function(t,n,e){
function o(n){t[n]=function(){t[e].push([n].concat(Array.prototype.slice.call(arguments,0)))}}
for(var a=0;a<n.length;a++)o(n[a])
}(a,["init","setUserIdentities","getUserIdentities"],"_q");
t.zeotapInteract=a;
window.zeotapInteract.init("<API_KEY>");
}(window,document);
</script>
Note:
- Replace
<API_KEY>with your Web Javascript API source key. - For identifier lookup, please set the first-party identifier on the page using our
setUserIdentitiesmethod. This identifier will be used for lookups on the Zeotap end.
The identifier keys you pass to setUserIdentities (or in the request body for direct API calls) must match the source field names configured for your write_key in the Zeotap dashboard. For example, if your source maps the identifier as user_id, you must use exactly user_id when calling setUserIdentities.
There is no error returned for unrecognized keys — the SDK silently drops them and the API returns 200 { interactions: [] }, indistinguishable from "user not found" or "no rules matched."
To verify your identifier is being sent correctly:
- Open your browser's network panel.
- Find the call to
/api/interact/interactions. - Inspect the
userobject in the request body. - Confirm each key exists in the source field configuration in the Zeotap dashboard.
This is the most common cause of empty results from the Interact SDK.
Retrieving Data on the Client Side Based on Configured “Data to send” for an Interaction
When you configure a Data type interaction in Zeotap, you choose how the resolved profile data is delivered to the page. There are four delivery methods:
In all four delivery methods, the data object is a flat key-value map:
{
"segment_membership": ["123", "456"],
"age_group": "25-34",
"custom_score": "high"
}
The keys are the destination field names you configure in the "Data to Send" mapping for the interaction. The values are the resolved profile attribute values for the current user.
Throughout this guide you'll see names like zeoParamsStoreLocal, zeoParamsStoreSession, zeoParamsGlobal, and zeoParamsCallback. These are Zeotap conventions — the recommended values for the corresponding fields in the dashboard, and what most partner integrations (GAM tag templates, Adobe Target wrappers, ad ops scripts) expect by default. They are not hardcoded in the SDK. You can configure any names you want in the dashboard, but downstream consumers must be updated to match.
1. Local Storage
Stores the selected data in local storage under the Zeotap key zeoParamsStoreLocal, which the consuming platform can access on the client side. Refer to the GAM implementation below for guidance on implementing a local storage-based workflow.
if (typeof Storage !== "undefined") {
var targetingParamStr = localStorage.getItem("zeoParamsStoreLocal");
if (targetingParamStr) {
var targetingParameters = JSON.parse(targetingParamStr);
// Use targetingParameters here
}
}
2. Session Storage
Stores the selected data in session storage under the Zeotap key zeoParamsStoreSession, which can be accessed by the consuming platform. Similar to local storage, you can push data to session storage and retrieve it as shown below.
if (typeof Storage !== "undefined") {
var targetingParamStr = sessionStorage.getItem("zeoParamsStoreSession");
if (targetingParamStr) {
var targetingParameters = JSON.parse(targetingParamStr);
// Use targetingParameters here
}
}
3. Global Variable
Writes the resolved data directly onto a named property of the window object. You configure the variable name in the Zeotap dashboard when setting up the interaction (under Data to Send → Set Global Attribute → Global Variable Name).
// Configured variable name in dashboard: "zeoParamsGlobal"
// After the SDK resolves the interaction, the variable is available as:
var targetingParameters = window.zeoParamsGlobal;
// { "segment_membership": ["123", "456"], "age_group": "25-34", ... }
Use zeoParamsGlobal as the Global Variable Name in the dashboard unless you have a specific reason not to. This is the established Zeotap convention — partner integrations (Adobe Target wrappers, GAM tag templates, ad ops scripts) often expect this exact name. Choosing a custom name means downstream consumers must be updated to read from your custom property.
Because the SDK runs asynchronously after your page loads, the variable may not be set at the exact moment your code runs. Use one of these patterns to handle timing:
Wait for the variable (polling):
function readZeotapGlobal(variableName, callback, maxWaitMs) {
var elapsed = 0;
var interval = 100; // check every 100 ms
var timer = setInterval(function () {
if (window[variableName] !== undefined) {
clearInterval(timer);
callback(window[variableName]);
}
elapsed += interval;
if (elapsed >= maxWaitMs) {
clearInterval(timer);
callback({}); // proceed without data
}
}, interval);
}
// Usage — wait up to 2 seconds
readZeotapGlobal("zeoParamsGlobal", function (targetingParameters) {
// Use targetingParameters here
}, 2000);
Read it inside a DOMContentLoaded or load handler (if your script runs in <head>):
window.addEventListener("load", function () {
var targetingParameters = window.zeoParamsGlobal || {};
// Use targetingParameters here
});
Use this delivery method when a third-party tag or analytics library on your page already reads from a known window.* variable by name (e.g., a pre-bid adapter, a tag manager data layer, or a custom analytics object). It requires no function contract — just agree on the variable name.
The variable is set once when the interaction qualifies on page load. It does not update reactively. For pages with dynamic content (SPAs), re-trigger the SDK on each navigation event.
4. Callback Function
Passes the selected data to the zeoParamsCallback() function, which can be directly accessed by the consuming platform on the client side.
window.zeoParamsCallbackCalled = false;
// fail-safe after 2 seconds
setTimeout(() => {
window.zeoParamsCallback({});
}, 2000);
window.zeoParamsCallback = function (targetingParameters) {
if (window.zeoParamsCallbackCalled) return;
window.zeoParamsCallbackCalled = true;
// Use targetingParameters here
};
Google Ad Manager Integration
Prerequisite
If you plan to send only Segment membership to Google Ad Manager (GAM), follow these steps:
- Create the required segments in Zeotap for tagging user profiles with segment memberships.
- Define and target key/value parameters in Google Ad Manager.
- For example, for segment membership, the key would be
"segment_membership", and the values would be the list of segment IDs the user is part of.
- For example, for segment membership, the key would be
Google Documentation (Recommended Reading):
Ensure Zeotap Interact SDK is implemented as described to work correctly.
Option 1: Callback
This solution fetches the current profile of the user (e.g., segment membership) and sends it to GAM. With this setup, ads will be displayed once Zeotap has rendered the profile information to GAM.
Place or trigger the following code after the Zeotap Interact SDK and GAM jsTag
window.zeoParamsCallbackCalled = false;
// fail-safe after 2 seconds
setTimeout(function () {
window.zeoParamsCallback({});
}, 2000);
window.zeoParamsCallback = function (targetingParameters) {
if (window.zeoParamsCallbackCalled) {
// callback already called
return;
}
window.zeoParamsCallbackCalled = true;
// Your Google Ad Manager code should go here, followed by
// Sending targeting params for this user to Google ad manager
if (window.googletag.pubads) {
Object.keys(targetingParameters).forEach((key) => {
window.googletag.pubads().setTargeting(key, targetingParameters[key]);
});
}
};
This ensures that ads are displayed only after the user's profile information has been updated in GAM, providing the platform with the most current data. However, if the timer expires without receiving a response, GAM will still render and display a default or generic banner (if setup). The drawback is that this may cause a delay before the ads are shown.
Option 2: Local Storage
This solution pushes profile information into local storage. Google Tag Manager can then read the targeting parameters from the browser’s local storage using the code provided below.
Place or trigger the following code after the Zeotap SDKs :
if (typeof Storage !== "undefined") {
var targetingParamStr = localStorage.getItem("zeoParamsStoreLocal");
if (targetingParamStr) {
var targetingParameters = JSON.parse(targetingParamStr);
// Place the below code after the GAM tag
if (window.googletag && window.googletag.pubads) {
Object.keys(targetingParameters).forEach((key) => {
window.googletag.pubads().setTargeting(key, targetingParameters[key]);
});
}
}
}
The benefit of this solution is that ads will be shown without delay for returning visitors or on subsequent page visits. However, the drawback is that first-time visitors to the landing page may not receive a personalized ad.
Option 3: Global Variable
If your Google Tag Manager container or GAM setup reads data from a named window variable, configure the interaction in Zeotap with Set Global Attribute and set the variable name to zeoParamsGlobal (the Zeotap convention).
// Place this after the Zeotap Interact SDK and before the GAM jsTag
function applyZeotapTargetingFromGlobal(variableName, maxWaitMs) {
var elapsed = 0;
var interval = 100;
var timer = setInterval(function () {
if (window[variableName] !== undefined || elapsed >= maxWaitMs) {
clearInterval(timer);
var params = window[variableName] || {};
if (window.googletag && window.googletag.pubads) {
Object.keys(params).forEach(function (key) {
window.googletag.pubads().setTargeting(key, params[key]);
});
}
}
elapsed += interval;
}, interval);
}
applyZeotapTargetingFromGlobal("zeoParamsGlobal", 2000);
This approach combines the immediacy of a callback with the simplicity of a global variable. Replace "zeoParamsGlobal" with a custom name only if your downstream consumers are already wired to a different property.
Adobe Target Integration
Prerequisite
If you plan to send only Segment membership to Adobe Target, follow these steps:
- Create the required segments in Zeotap for tagging user profiles with segment memberships.
- Define and target key/value parameters in Adobe Target.
- For example:
- If you have defined the key as
"segment_membership"in both Adobe and Zeotap, the value received will be a list of segment IDs associated with a user. - The key format depends on your Adobe Target setup:
- If targeting is configured with the key as
visitor profile, you must send it on the client side asprofile.segment_membership. - If it’s set up as a custom key, you can simply send it as
segment_membership.
- If targeting is configured with the key as
- If you have defined the key as
- For example:
Adobe Documentation:
- You can refer the official Adobe Documentation Link here
Serve without delay
This solution pushes profile information into local storage. Adobe Target can then read the targeting parameters from the browser’s local storage using the code provided below.
Place or trigger the following code after the Zeotap SDKs, Adobe Target is loaded:
window.targetPageParams = function () {
// read data from local storage
if (typeof Storage !== "undefined") {
var targetingParamStr = localStorage.getItem("zeoParamsStoreLocal");
if (targetingParamStr) {
try {
const params = JSON.parse(targetingParamStr);
return { ...params };
} catch (e) {
console.error(e);
return {};
}
}
}
return {};
};
The benefit of this solution is that ads will be shown without delay for returning visitors or on subsequent page visits. However, the drawback is that first-time visitors to the landing page may not receive a personalized ad.
Serve with a Global Variable
If Adobe Target reads from a named window variable, configure the interaction with Set Global Attribute:
window.targetPageParams = function () {
return window.zeoParamsGlobal || {};
};
window.targetPageParams is evaluated by at.js when it fires. If zeoParamsGlobal is set before at.js runs, you get the data with no delay. Load order matters: place the Zeotap Interact SDK tag before the Adobe at.js tag.