CleverTap

Datafly Signal delivers events to CleverTap server-to-server using the Upload Events API (POST /1/upload). Events are keyed on each user’s identity, matched to their CleverTap profile, and made available for segmentation, journeys, and omnichannel campaigns — without a client-side tag.

Prerequisites

Before configuring CleverTap in Signal you need a CleverTap account and its server-side API credentials.

Find your Account ID and Passcode

  1. Sign in to the CleverTap dashboard.
  2. Go to Settings > Engagement > A/c Info (Account Info).
  3. Note the Account ID (also called the Project ID) and the Passcode (the Account Passcode, or a user-scoped passcode if your organisation uses per-user passcodes).

Identify your region

CleverTap provisions every account in a single data region. The region determines the API host you must send to.

Region codeData centre
us1United States
in1India
eu1Europe
sg1Singapore
aps3Asia-Pacific
mec1Middle East

Your region is shown in the dashboard URL and under Settings. Sending to the wrong region results in authentication failures.

Configure in Signal

Configuration Fields

FieldRequiredDescription
account_idYesYour CleverTap Account ID (Project ID). Sent as the X-CleverTap-Account-Id header.
passcodeYesYour CleverTap Account Passcode. Sent as the X-CleverTap-Passcode header.
regionYesYour account’s data region: one of us1, in1, eu1, sg1, aps3, mec1. Sets the API host.

Management UI Setup

  1. Go to Integrations > Add Integration > CleverTap.
  2. Choose the Default preset.
  3. Enter your account_id, passcode, and region.
  4. Select consent categories (typically marketing).
  5. Click Save.

API Endpoint

POST https://{region}.api.clevertap.com/1/upload

Required headers:

X-CleverTap-Account-Id: {account_id}
X-CleverTap-Passcode: {passcode}
Content-Type: application/json; charset=utf-8

Events are sent as a JSON object with a d array. Up to 1,000 records may be sent per request, and CleverTap allows up to 15 concurrent requests per account. Signal batches and rate-limits automatically.

Identity Signals

CleverTap matches each event to a user profile using one of the identity fields below. You must supply at least one. Signal sends them at the record level.

FieldSource in SignalDescription
identityemail from datafly.identify()The primary user identifier. Use the same value your CleverTap SDK uses so server and client events merge into one profile.
objectIdDatafly user_idCleverTap’s internal Global Object ID, used when you already have a CleverTap-issued ID.
⚠️

The identity you send must match the identifier your app’s CleverTap SDK uses (typically the user’s email or your own customer ID). If they differ, server events create a separate profile instead of merging with the user’s existing one.

CleverTap does not hash identity fields — they are stored as-is for matching. To send identity, call datafly.identify() when a user logs in or registers:

datafly.identify("user-123", {
  email: "jane.doe@example.com"
});

Event Mapping

Signal’s GA4-style event names are mapped to CleverTap custom event names. Properties are sent inside evtData. The Default preset includes:

Signal eventCleverTap event
pageWeb Page Viewed
Products SearchedSearched
Product ViewedProduct Viewed
Product Added to WishlistAdded to Wishlist
Product AddedAdded to Cart
Checkout StartedCheckout Started
Order CompletedCharged
Signed UpSigned Up
Logged InLogged In

Charged is CleverTap’s reserved purchase event. Signal maps Order Completed to Charged with Amount, Currency, and a Charged ID, and passes line items as Items so revenue and order analytics work out of the box.

To customise, edit the integration’s Field Mappings in the Management UI.

Example: Purchase Event

Datafly.js call:

datafly.track("Order Completed", {
  order_id: "ORD-001",
  revenue: 129.99,
  currency: "USD",
  products: [
    { product_id: "SKU-A", name: "Widget", price: 49.99, quantity: 2 },
    { product_id: "SKU-B", name: "Gadget", price: 30.01, quantity: 1 }
  ]
});

CleverTap payload sent by Signal:

{
  "d": [
    {
      "type": "event",
      "identity": "jane.doe@example.com",
      "ts": 1706540000,
      "evtName": "Charged",
      "evtData": {
        "Charged ID": "ORD-001",
        "Amount": 129.99,
        "Currency": "USD",
        "Items": [
          { "product_id": "SKU-A", "name": "Widget", "price": 49.99, "quantity": 2 },
          { "product_id": "SKU-B", "name": "Gadget", "price": 30.01, "quantity": 1 }
        ]
      }
    }
  ]
}

Testing Your Integration

  1. Trigger an event on your site (e.g. complete a test order).
  2. In the CleverTap dashboard, open the user’s profile (search by the identity you sent) and confirm the event appears under Events.
  3. Inspect the raw response in Signal’s event debugger — a clean delivery returns HTTP 200 with:
{ "status": "success", "processed": 1, "unprocessed": [] }
⚠️

CleverTap returns HTTP 200 even when individual records are rejected. A status of partial or fail (with entries in unprocessed) means the event was not stored — Signal treats only status: success as a successful delivery and will surface partials as errors.

Troubleshooting

ProblemSolution
401 UnauthorizedCheck the Account ID and Passcode, and confirm the region matches the account’s data centre. A wrong region looks like bad credentials.
Events stored under a new/empty profileThe identity sent does not match the value your CleverTap SDK uses. Align both on the same email or customer ID.
status: partial / fail in the responseInspect the unprocessed array — usually a missing identity, an invalid property value (max 512 bytes), or a reserved/over-limit event name.
429 Too Many RequestsYou have exceeded the 15 concurrent requests per account limit. Reduce delivery concurrency for the integration.
Purchase revenue not showingEnsure Order Completed maps to Charged with Amount and Currency populated — these are CleverTap’s reserved revenue fields.