SetupWordPress Setup

WordPress Setup

Install the CleanClicks WordPress plugin for automatic tracking, WooCommerce event capture, server-side conversion webhooks, and analytics proxy integration.

CleanClicks ships a dedicated WordPress plugin. The current Signal and Clarity plans support the guided WordPress and WooCommerce path. Available features still depend on the selected plan, current plugin version, domain configuration, consent state, and connected destinations.

The CleanClicks WordPress plugin is the full integration. It auto-creates the WooCommerce conversion webhook on activation, auto-derives your site domain, applies smart defaults when your CleanClicks account is fully configured, and shows live setup status in the admin UI.

Download and Install

  1. In your CleanClicks dashboard, go to Configuration → Ecommerce tab
  2. Click Download Plugin to get the current plugin zip
  3. In WordPress Admin, go to Plugins → Add New → Upload Plugin
  4. Choose the zip and click Install Now
  5. Click Activate

Configure the Plugin

After activation:

  1. In your WordPress Admin sidebar, click CleanClicks
  2. Enter your Inbound API Key (copy it from CleanClicks → Configuration → Inbound keys tab)
  3. Click Save Changes

That's it. The plugin auto-detects your site domain from home_url() (stripping a leading www. for WP Engine and similar www-subdomain installs), fetches your CleanClicks configuration on activation, and begins tracking immediately.

What Happens Automatically on Activation

The plugin does several things on first activation so you don't have to:

  • Domain auto-detection — your CleanClicks proxy origin (https://cleanclicks.yourdomain.com) is derived from home_url(). No "Client Domain" field to fill in.
  • Remote config fetch — the plugin calls your CleanClicks /__cc/wp-config endpoint and caches the response for 1 hour, so the first page request doesn't pay the round trip.
  • GA4 First-Party Proxy on by default — the plugin serves GA4 through your own domain from the start, and skips itself if that measurement ID is already firing on your site.
  • WooCommerce webhook auto-create — if WooCommerce is active, the plugin creates the order.created webhook for you, pointed at your CleanClicks proxy with the correct signing secret. No manual webhook setup required.
  • Onboarding banner — if you haven't entered your Inbound API Key yet, the plugin shows a banner on the settings page walking you through the one-step setup.

Smart defaults are gated server-side and preserve customer choice on updates and reactivations — your existing settings are never overwritten by a plugin update.

Webhook Status Card

The plugin settings page includes a live Webhook Status card showing the current state of the auto-created WooCommerce webhook:

StateWhat It Means
ActiveWebhook is created in WC, pointed at your CleanClicks proxy, signed with your Inbound API Key. Nothing to do.
Missing — no API keyEnter your Inbound API Key in the settings above and save. The webhook will create on the next page load.
Missing — WC not loadedWooCommerce isn't active yet. Activate WooCommerce and the webhook will create on the next page load.
Missing — pending creationThe plugin flagged the webhook for creation but WooCommerce hadn't loaded at activation time. It will create on the next request.
Missing — deleted externallySomeone manually deleted the webhook from WooCommerce → Settings → Advanced → Webhooks. Click Recreate to restore it.
ErrorThe plugin tried to create the webhook and WooCommerce returned an error. The card shows the last error message.

If the webhook ever drifts (e.g., you delete it manually), click Recreate Webhook on the status card to restore it.

What the Plugin Tracks

FeatureTriggerPlan Gate
Pageview trackingEvery page loadSignal or Clarity
Click ID captureURL parameters (gclid, fbclid, ttclid, tbclid, li_fat_id, msclkid, wbraid, gbraid)Signal or Clarity
Email identity hashing (SHA-256)Form submissions + WooCommerce checkoutSignal or Clarity
Conversion event postingpurchase, view_item, add_to_cart, begin_checkout, custom triggersSignal or Clarity
view_itemSingle product pagesSignal or Clarity with WooCommerce
view_item_listShop, category, tag archive pagesSignal or Clarity with WooCommerce
add_to_cartAJAX and form-based add-to-cartSignal or Clarity with WooCommerce
remove_from_cartCart item removalSignal or Clarity with WooCommerce
begin_checkoutCheckout page load + checkout-intent click from cartSignal or Clarity with WooCommerce
purchaseOrder completed (client-side + server-side webhook)Signal or Clarity with WooCommerce
GA4 First-Party ProxyRoutes GA4 client-side traffic through cleanclicks.yourdomain.comSignal or Clarity
Usermaven ProxyFirst-party Usermaven trackingSignal or Clarity
Plerdy ProxyFirst-party Plerdy trackingSignal or Clarity
WP Consent API integrationHonors consent state from compatible CMPsSignal or Clarity

Every event includes enhanced product data: SKU, brand (YITH or product taxonomy), up to 5 category levels, and variant info for variable products.

Server-Side Conversion Capture

The plugin uses three coordinated WooCommerce order paths: two server-side, plus a client-side fallback for custom thank-you pages. The two server-side paths post to the same CleanClicks webhook endpoint, /__cc/woocommerce/webhook, where CleanClicks de-duplicates by order ID so one order produces one conversion.

Layer 1: Auto-Webhook (order.created)

On activation, the plugin creates a WooCommerce webhook with these properties:

  • Topic: Order created
  • Delivery URL: https://cleanclicks.yourdomain.com/__cc/woocommerce/webhook
  • Secret: your Inbound API Key (the same key signs the webhook and authorizes inbound API calls — one key, two jobs)

This is the primary capture path for the standard WooCommerce checkout flow. You can verify the webhook exists in WordPress Admin → WooCommerce → Settings → Advanced → Webhooks — look for "CleanClicks Conversion Capture" with topic "Order created."

Layer 2: woocommerce_payment_complete Hook

The plugin hooks the WooCommerce payment_complete action with a fire-and-forget POST to the same webhook endpoint. This backstops three scenarios where the order.created webhook isn't enough:

  • Subscription renewals — woocommerce_payment_complete fires when a renewal payment is captured by the cron, even with no customer browser session present.
  • Offsite checkout returns — when a customer is bounced to an external payment processor (PayPal, Klarna, etc.) and returns, the standard webhook may fire before payment is confirmed. The payment_complete hook fires on actual payment.
  • Custom thank-you flows — sites with non-standard order-completion pages (membership signups, custom landing pages) where the client-side purchase event might not fire.

CleanClicks de-duplicates by order ID across Layer 1 and Layer 2, using a 48-hour order dedupe window (configurable up to 7 days). Whichever path arrives first creates the conversion. A later arrival for the same order inside that window is logged as a duplicate and never uploaded to your platforms.

Layer 3: Configurable purchase_paths Allowlist

On every front-end page load, the plugin checks the current URL against an allowlist of paths that indicate a purchase-completion page. When matched, it fires a purchase event for the relevant order. Defaults:

/order-received/
/thank-you/
/order-confirmation/
/my-account/view-subscription/

This catches custom thank-you pages that don't trigger the standard woocommerce_thankyou hook.

Configuring Custom Thank-You Paths

If your site uses a custom thank-you URL pattern (e.g., a checkout flow that redirects to /platinum-thank-you/{order_id}/), add it on the plugin settings page under Custom Thank-You Paths. One path per line, substring match.

Example: scm-platinum custom flow. Sports Car Market's premium subscription flow redirects to URLs like /scm-platinum-thanks/12345. To capture those, set:

  • Custom Thank-You Paths: add /scm-platinum-thanks/ on its own line
  • Custom Thank-You Regex (advanced): ^/scm-platinum-thanks/[0-9]+

The regex is optional. Substring matching covers most cases; regex is for surgical patterns where substring would over-match.

Programmatic Extension

If you need to extend purchase_paths from a child theme or companion plugin instead of through the admin UI, three filter hooks are available:

  • cleanclicks_purchase_paths — modify the path allowlist array
  • cleanclicks_purchase_path_regex — set or override the regex pattern
  • cleanclicks_resolve_order_id — supply a custom order-ID resolver for the matched page

This section lists what the plugin stores and how it reads consent. It does not decide your legal basis or your consent categories; those stay your decision.

The plugin declares its own storage to the WP Consent API as functional. CMPs that integrate with the WP Consent API (CookieYes, Cookiebot, Complianz, iubenda, and others) read that classification.

Two of the five are cookies:

NameLifetimeWhat It Holds
cc_pid1 yearAnonymous visitor identifier, used for conversion deduplication
cc_ss_optout1 yearThe visitor-controlled privacy opt-out flag

The other three are browser storage, not cookies:

NameWhereLifetimeWhat It Holds
cc_click_idslocalStorage90 daysAd click identifiers captured from URL parameters
cc_attributionlocalStorage30 daysUTM parameters, referrer, and landing page
cc_session_idsessionStorageSessionGroups page views within one visit

The plugin registers itself with the WP Consent API as the cleanclicks service. On WP Consent API v2.0 and later it checks service-level consent (wp_has_service_consent("cleanclicks")) ahead of the category check, so a visitor can grant or deny CleanClicks on its own in a Complianz, CookieYes, or iubenda service toggle without touching your other analytics tools. On v1.x it falls back to the category check (statistics by default). When consent is required and no consent API is present at all, the plugin blocks analytics dispatch rather than assuming a grant.

OneTrust Bridge

OneTrust does not integrate with the WP Consent API on its own, so the plugin bridges the two for you. It reads OnetrustActiveGroups and maps OneTrust's category IDs onto wp_set_consent() calls, syncing on page load, on a OneTrustGroupsUpdated dataLayer push, and through OneTrust.OnConsentChanged(). OneTrust customers do not need to paste a custom snippet.

For per-CMP configuration guidance, see CMP Configuration.

Option B: Manual Tag Installation

If you don't want to install the plugin — for example, if you don't have WooCommerce and only need basic page-view + click-ID tracking — you can install the CleanClicks tag manually.

Using a Theme Header

  1. In WordPress Admin, go to Appearance → Theme File Editor
  2. Open header.php (or your theme's equivalent head template)
  3. Add the script tag before </head>:
<script src="https://cleanclicks.yourdomain.com/__cc/cc.js" defer></script>
  1. Click Update File

Using a Header Scripts Plugin

If you don't want to edit theme files:

  1. Install a plugin like WPCode (formerly "Insert Headers and Footers") or similar
  2. Add the CleanClicks script tag to the header section
  3. Save

Manual installation captures click IDs, attribution, and conversions on the standard /__cc/conv endpoint, but you lose the WooCommerce event capture, server-side webhook auto-create, analytics proxy injection, and admin status UI that ship with the plugin.

Plugin Updates

When updating the plugin:

  1. Deactivate the current version in WordPress Admin → Plugins
  2. Delete it
  3. Upload the new version via Plugins → Add New → Upload Plugin
  4. Activate

Don't use WordPress's "Replace current with uploaded" feature — it's unreliable. Always deactivate, delete, and re-upload.

Updates preserve your existing settings. Smart defaults only apply on fresh installs (where no cleanclicks_settings option exists). If you've configured the plugin manually, your configuration is sacred and never overwritten on update.

After updating, clear all cache layers in this order:

  1. Your caching plugin (WP Rocket, W3 Total Cache, etc.)
  2. Your hosting CDN cache (WP Engine, Kinsta, Cloudflare, etc.)
  3. Your browser cache (hard refresh or Incognito test)

Verify by viewing page source and checking that the ?ver= parameter on the CleanClicks script tag matches the new version number.

Troubleshooting

IssueSolution
Plugin won't activateVerify PHP 7.4+. Check your error log for class-name collisions with other plugins (CleanClicks uses the CLEANCLICKS_ prefix to avoid conflicts but a third-party plugin may use the same identifier).
Events not firingVerify your domain is Active in CleanClicks. Check browser DevTools → Network for cleanclicks.yourdomain.com/__cc/cc.js returning 200. Verify the ?ver= parameter matches the installed plugin version (mismatch means cache is stale — clear all cache layers).
Webhook Status card shows "Missing — deleted externally"Click Recreate Webhook on the card. The plugin will re-create the order.created webhook with the correct signing secret.
WooCommerce events missingConfirm WooCommerce is active. Verify the plugin's WooCommerce integration loaded — the plugin settings page shows "WooCommerce: Active" when detected.
Purchase events missing on custom thank-you pagesAdd your custom URL pattern to Custom Thank-You Paths on the plugin settings page (see Layer 3 above).
Stale JavaScript after updateCheck the ?ver= query string in page source. If it matches the old version, the version didn't bump — verify the new plugin version installed. If correct but content is stale, clear caching plugin + CDN + browser cache.
Analytics proxies not loadingVerify GA4 or Usermaven is configured in CleanClicks → Configuration → Vendors. Then in WordPress Admin → CleanClicks, open Advanced settings and confirm the matching box is ticked under Analytics Proxies (GA4 First-Party Proxy, Usermaven Proxy, or Plerdy Proxy). Note: analytics proxies require Signal or Clarity plan.
Site is on www.example.com and proxy origin looks wrongThe plugin strips the leading www. when it derives the origin, so www.example.com becomes cleanclicks.example.com. If the origin still looks wrong, download the current plugin from your dashboard and reinstall.
GA4 events show as "Unassigned"Confirm you are looking at the GA4 property the plugin is configured against, and that GA4 First-Party Proxy is ticked so client-side events keep their traffic source. Installing the plugin is not on its own a reason to change the GA4 server-side setting. If GA4 shows duplicate purchases, contact support. See GA4 Connections.

Next: Configuration — Vendors | CMP Configuration