WooCommerce

PennyLens auto-detects WooCommerce stores running WC 8.x, 9.x, and 10.x. Drop the standard SDK snippet onto your store and the e-commerce events — cart_add, checkout_started, purchase — start flowing without any further wiring.

This page covers what auto-detect actually does, where it can fall short, and how to recover when it does.

When auto-detect activates

When the SDK loads on a page, it checks three signals. Any single positive is enough to enable the WooCommerce hooks:

  • woocommerce-checkout body class — present on the checkout page across virtually every theme, because WooCommerce sets it through its own filter.
  • window.wc.wcBlocksRegistry — present on stores using the Blocks checkout.
  • A /wp-content/plugins/woocommerce script tag — catches WC core scripts even when the other signals are absent.

The check runs cheapest-first, short-circuits on the first positive, and silently no-ops on non-WooCommerce sites. The auto-detect logic is part of the core 8 KB SDK bundle and contributes zero runtime cost on non-WC pages.

Dual-listener mechanism for cart_add

WooCommerce has two distinct checkout stacks, and PennyLens listens to both:

Legacy themes (jQuery added_to_cart)

Most themes built before Blocks — Storefront, Astra, Divi, and similar — dispatch the jQuery added_to_cart event when a product is added. PennyLens reads product_id and quantity from the add-to-cart button's data-* attributes and emits a fully-populated cart_add event.

Blocks checkout (wc-blocks_added_to_cart DOM event)

Blocks checkout dispatches wc-blocks_added_to_cart as a standard DOM event — but the payload is empty due to a known WooCommerce upstream issue. PennyLens still emits the cart_add event so the dashboard can count it; the product_id field is null in this case.

Even with a null product_id, the dashboard's visitor-level metrics — cart abandonment rate, average order value, checkout conversion — work correctly because they count visitors, not line items. If you need per-product cart tracking on a Blocks-only store, use the manual snippet in the SDK reference.

Mutual exclusion with Shopify

If both Shopify and WooCommerce signals appear on the same page — usually only on agency development sites — the WooCommerce auto-hook silently no-ops and Shopify takes precedence. Exactly one network-level interceptor is installed per page. Manual wiring still works on these dual-signal sites if you need it.

Zero-event fallback

If 24 hours after install you don't see any events in the PennyLens dashboard, walk through these checks in order:

  1. Confirm the SDK is loaded. Open your browser's developer console on the store and run window.PennyLens. It should be defined.
  2. Check for a custom checkout endpoint. If you've renamed the order-received page under Settings → Advanced → Page setup, the URL-only fallback for purchase events won't fire — but the body class and AJAX interceptor still will. In your browser's Network tab during a test checkout, confirm requests to either /wc-ajax/?wc-ajax=checkout or /wp-json/wc/store/v1/checkout are visible.
  3. Check the body class. Some heavily customized themes strip the woocommerce-checkout body class. If that's true AND your store doesn't use Blocks checkout AND no /wp-content/plugins/woocommerce script loads on the checkout page, auto-detect won't activate. Fall back to manual wiring through the SDK reference — usually a small snippet in functions.php.

Confidence indicator

Once at least one cart_add or purchase event has arrived, the dashboard Overview displays a confidence badge above the KPI row:

WooCommerce detected — 1,247 events captured

The badge is informational — no action required when it appears. The data is flowing. If you don't see the badge after 24 hours, return to the Zero-event fallback above.

Manual wiring

If your store falls outside the auto-detect signals — heavily customized themes, headless WooCommerce setups, or Blocks stores that need per-product cart tracking — wire the events manually:

pennylens.track("cart_add", {
  product_id: 4218,
  qty: 1,
  total: 89.99,
  currency: "USD",
});

Same API as any custom event. See Event Tracking for the full reference.

Next steps