Basic CAPI Installation

Install SignalSight conversion tracking on your website — loader snippet, PageView, and copy-ready p2sq.push() examples for every standard event. Transition guide from Meta Pixel and TikTok Pixel.

In This Page

Introduction

This guide explains how to integrate SignalSight conversion tracking into your website source code. After creating a tracker in the dashboard, add the loader snippet and event calls below to send server-side events to Meta, TikTok, and other connected platforms.

Before You Start

Remove duplicate pixel calls

When adding SignalSight events, remove all fbq calls but keep the Facebook loading code. Remove all ttq calls but keep the TikTok loading code. SignalSight replaces the event firing — duplicate calls cause double counting.

Remove the following Facebook block (keep only the loader, not fbq('init') / fbq('track')):

Remove — fbq init & track
<script>
  fbq('init', 'your-pixel-id');
  fbq('track', 'PageView');
</script>

If you already have TikTok Pixel or Events API integration, remove ttq.load and ttq.page but keep the TikTok analytics loader:

Remove — ttq.load & ttq.page
<script>
  ttq.load('YOUR PIXEL ID WILL BE LOCATED HERE');
  ttq.page();
</script>

Events

Implement the following events on your website:

  1. Loading Code and Page View Event
  2. View Content Event
  3. Custom Special Event
  4. Search Event
  5. Add To Cart Event
  6. Initiate Checkout Event
  7. Purchase Event
  8. Lead Event
  9. Complete Registration Event
  10. Contact Event

1. Loading Code and Page View Event

Place the Facebook pixel loader at the top of every page. Remove any existing fbq('track', 'PageView') call to prevent duplicate PageView events.

Facebook Pixel loader (no fbq calls)
<!-- Facebook Pixel Code -->
<script>
  !function(f,b,e,v,n,t,s)
  {if(f.fbq)return;n=f.fbq=function(){n.callMethod?
  n.callMethod.apply(n,arguments):n.queue.push(arguments)};
  if(!f._fbq)f._fbq=n;n.push=n;n.loaded=!0;n.version='2.0';
  n.queue=[];t=b.createElement(e);t.async=!0;
  t.src=v;s=b.getElementsByTagName(e)[0];
  s.parentNode.insertBefore(t,s)}(window, document,'script',
  'https://connect.facebook.net/en_US/fbevents.js');
</script>
<!-- End Facebook Pixel Code -->

For TikTok Events API

If you use TikTok Events API, place the TikTok loading code immediately after the Facebook pixel loader and before the SignalSight JS code. Remove ttq.load and ttq.page to prevent duplicate events:

TikTok Pixel loader (no ttq calls)
<!-- Tiktok Pixel Code -->
<script>
  !function(w, d, t) {
    w.TiktokAnalyticsObject = t;
    var ttq = w[t] = w[t] || [];
    ttq.methods = ["page","track","identify","instances","debug",
      "on","off","once","ready","alias","group","enableCookie","disableCookie"];
    ttq.setAndDefer = function(t, e) {
      t[e] = function() {
        t.push([e].concat(Array.prototype.slice.call(arguments, 0)));
      };
    };
    for (var i = 0; i < ttq.methods.length; i++)
      ttq.setAndDefer(ttq, ttq.methods[i]);
    ttq.instance = function(t) {
      for (var e = ttq._i[t] || [], n = 0; n < ttq.methods.length; n++)
        ttq.setAndDefer(e, ttq.methods[n]);
      return e;
    };
    ttq.load = function(e, n) {
      var i = "https://analytics.tiktok.com/i18n/pixel/events.js";
      ttq._i = ttq._i || {};
      ttq._i[e] = [];
      ttq._i[e]._u = i;
      ttq._t = ttq._t || {};
      ttq._t[e] = +new Date;
      ttq._o = ttq._o || {};
      ttq._o[e] = n || {};
      var o = document.createElement("script");
      o.type = "text/javascript";
      o.async = !0;
      o.src = i + "?sdkid=" + e + "&lib=" + t;
      var a = document.getElementsByTagName("script")[0];
      a.parentNode.insertBefore(o, a);
    };
  }(window, document, 'ttq');
</script>
<!-- End Tiktok Pixel Code -->

After the pixel loaders, add the SignalSight loader. Replace your-p2s-key with the key from your tracker detail page in the dashboard:

SignalSight loader + Init + PageView
<!-- BEGIN Signalsight Loader Code -->
<script language="JavaScript" type="text/JavaScript">
  window.p2sq = window.p2sq || [];
  p2sq.push({
    et: 'Init',
    p: {
      em: '{user-email}',         // Parameters
      fn: '{user-first-name}',    // encrypted
      ln: '{user-last-name}'      // with SHA-256
      // ...
    }
  });

  p2sq.push({ et: 'PageView' });  // Page View Event

  !function(f, b, e, v, t, s) {
    f.p2sq = f.p2sq || [];
    if (f.p2sf) return;
    f.p2sf = true;
    t = b.createElement(e);
    t.async = !0;
    t.src = v;
    s = b.getElementsByTagName(e)[0];
    s.parentNode.insertBefore(t, s);
  }(window, document, 'script', 'https://cpi.ssevt.com/js/v4.2/your-p2s-key');
</script>
<!-- END Signalsight Loader Code -->

Google Tag Manager users

If you implement these snippets in Google Tag Manager, replace each placeholder with the matching GTM variable using double curly braces. For example, change {user-email} to {{user-email}}, {product-id} to {{product-id}}, and {currency} to {{currency}}. The single-brace placeholders in the examples below are for direct source-code installs — in GTM, wire each value to a Data Layer Variable or built-in variable.

Parameter List
User informationParameterFormatExample
E-mailemLowercase + SHA256 hash[email protected]
First namefnLowercase + SHA256 hashjohn
Last namelnLowercase + SHA256 hashdoe
TelephonephOnly numbers including country and area code + SHA256 hash12125357525
GendergeA single lowercase letter f or m + SHA256 hashf
BirthdaydbOnly numbers: year, month, day + SHA256 hash19910526 for May 26, 1991
CityctLowercase, no spaces + SHA256 hashnewyork
Postal / zip codezpOnly numbers + SHA256 hash34000
CountrycnTwo-letter country code, lowercase + SHA256 hashtr

Client-Side PII Hashing

If you cannot hash PII on the server, hash it in the browser. Load this script at the top of every page, before the SignalSight loader:

js-sha256 library
<script src="https://cdnjs.cloudflare.com/ajax/libs/js-sha256/0.9.0/sha256.min.js"
  crossorigin="anonymous"></script>

Then update the Init block to use the sha256() function:

Init with client-side hashing
p2sq.push({
  et: 'Init',
  p: {
    em: sha256('[email protected]'),
    fn: sha256('John'),
    ln: sha256('Doe')
    // ...
  }
});

Tip

For server-side hashing workflows and a live verification tool, see the PII Hashing guide.

2. View Content Event

ViewContent
<script language="JavaScript" type="text/JavaScript">
  window.p2sq = window.p2sq || [];
  p2sq.push({
    et: 'ViewContent',
    p: {
      contents: [{ id: '{product-id}', quantity: 1 }],
      content_type: 'product',
      value: productPrice,                  // Price, e.g. 9.90
      currency: '{currency}',               // 3 Letter Currency Code, e.g. USD
      content_name: '{product-name}',        // Optional Parameters
      content_category: '{product-category}' // Optional Parameters
      // ...
    }
  });
</script>

3. Custom Special Event

Without parameters:

Custom:Special — minimal
<script language="JavaScript" type="text/JavaScript">
  window.p2sq = window.p2sq || [];
  p2sq.push({ et: 'Custom:Special' });
</script>

With optional parameters in the p object:

Custom:Special — with payload
<script language="JavaScript" type="text/JavaScript">
  window.p2sq = window.p2sq || [];
  p2sq.push({
    et: 'Custom:Special',
    p: {
      optionalParameter: anyValue
    }
  });
</script>

4. Search Event

Search
<script language="JavaScript" type="text/JavaScript">
  window.p2sq = window.p2sq || [];
  p2sq.push({
    et: 'Search',
    p: {
      search_string: '{search-string}',
      contents: [
        { id: '{product-1-id}', quantity: 1 },
        { id: '{product-2-id}', quantity: 1 }
      ],
      value: productPrice,                    // Price, e.g. 9.90
      currency: '{currency}',                 // 3 Letter Currency Code, e.g. USD
      content_category: '{product-category}'  // Optional Parameters
      // ...
    }
  });
</script>

5. Add To Cart Event

AddToCart
<script language="JavaScript" type="text/JavaScript">
  window.p2sq = window.p2sq || [];
  p2sq.push({
    et: 'AddToCart',
    p: {
      contents: [
        { id: '{product-1-id}', quantity: 1 },
        { id: '{product-2-id}', quantity: 1 }
      ],
      content_type: 'product',
      value: productPrice,    // Price, e.g. 9.90
      currency: '{currency}' // 3 Letter Code, e.g. USD
    }
  });
</script>

6. Initiate Checkout Event

InitiateCheckout
<script language="JavaScript" type="text/JavaScript">
  window.p2sq = window.p2sq || [];
  p2sq.push({
    et: 'InitiateCheckout',
    p: {
      contents: [
        { id: '{product-1-id}', quantity: 1 },
        { id: '{product-2-id}', quantity: 1 }
      ],
      value: productPrice,                    // Price, e.g. 9.90
      currency: '{currency}',                 // 3 Letter Currency Code, e.g. USD
      content_category: '{product-category}',  // Optional Parameters
      num_items: '{item-count}'              // Optional Parameters
      // ...
    }
  });
</script>

7. Purchase Event

Order ID required

Always pass a unique eid (order ID) on Purchase events — it is used for deduplication between browser and server events.

Purchase
<script language="JavaScript" type="text/JavaScript">
  window.p2sq = window.p2sq || [];
  p2sq.push({
    et: 'Purchase',
    p: {
      contents: [
        { id: '{product-1-id}', quantity: 1 },
        { id: '{product-2-id}', quantity: 1 }
      ],
      content_type: 'product',
      value: productPrice,    // Price, e.g. 9.90
      currency: '{currency}'  // 3 Letter Currency Code, e.g. USD
    },
    eid: '{order-id}'          // Unique Order ID – Important
  });
</script>

8. Lead Event

Lead
<script language="JavaScript" type="text/JavaScript">
  window.p2sq = window.p2sq || [];
  p2sq.push({
    et: 'Lead',
    p: { // Optionally the following parameters might be sent:
      content_name: '{product}', // Name of the page, product or form
      currency: '{currency}',    // 3 Letter Currency Code, e.g. USD
      value: productPrice        // Price, e.g. 9.90
    }
  });
</script>

9. Complete Registration Event

CompleteRegistration
<script language="JavaScript" type="text/JavaScript">
  window.p2sq = window.p2sq || [];
  p2sq.push({
    et: 'CompleteRegistration',
    p: { // Optionally the following parameters might be sent:
      content_name: '{product}',  // Name of the registration form
      currency: '{currency}',     // Three Letter Currency Code, e.g. USD
      value: productPrice,        // Price, e.g: 9.90
      status: status              // Boolean status: whether the registration
                                  // is actually completed
    }
  });
</script>

10. Contact Event

Contact
<script language="JavaScript" type="text/JavaScript">
  window.p2sq = window.p2sq || [];
  p2sq.push({ et: 'Contact' });
</script>

Only activate tracking scripts after the user has given consent through your Consent Management Platform (CMP). SignalSight respects your consent configuration.

Frequently Asked Questions

Why should I remove fbq and ttq calls but keep the loaders?

SignalSight takes over event firing server-side. Keeping the pixel loaders maintains browser compatibility while removing fbq/ttq track calls prevents duplicate events.

Where do I find my-p2s-key?

Open your tracker in the SignalSight dashboard. The installation snippet on the tracker detail page contains your unique key in the loader URL.

Should I hash PII before passing it to p2sq.push?

Yes. Email, phone, name, and other personal fields must be SHA256-hashed after normalization. Hash server-side when possible, or use the client-side sha256 library shown above.

Is this the same as the Transition Guide?

Yes. This page is the full Transition Guide referenced from the Meta CAPI Setup docs — copy-ready snippets for replacing Meta Pixel and TikTok Pixel event calls with SignalSight.