CMS & blogs · 3 min setup
How to add analytics to WordPress
wp_head hook in your child theme's functions.php. Either way it lands in the <head> of every page and survives theme updates.Updated
There's no VisitTrack plugin to install and keep updated — the tracker is one script tag. Avoid editing header.php directly: block themes (Twenty Twenty-Four, Twenty Twenty-Five and most new themes) don't have one, and on classic themes the edit disappears with the next theme update unless you use a child theme.
WordPress at a glance
- Easiest
- WPCode → Header & Footer → Header
- Code route
wp_headhook in a child theme or snippets plugin- Block themes
- Supported (no
header.phpneeded) - WordPress.com
- Needs a plan that allows plugins or custom code
- Caching plugins
- Exclude
tracker.jsfrom "delay JavaScript" features
How to install VisitTrack on WordPress
Step 1: Copy your site id
Add your WordPress site in VisitTrack and copy the snippet from the install step (or Settings → General). Replace
SITE_IDbelow.Step 2: Option A — use a header-code plugin
In wp-admin, go to Plugins → Add New, install and activate WPCode (formerly Insert Headers and Footers). Open Code Snippets → Header & Footer, paste the snippet into Header, and save. Other header/footer plugins work the same way. The first line is the optional queue stub, which lets inline calls (like the WooCommerce snippet below) run before the deferred script has loaded.
WPCode → Header<script>window.visitrack=window.visitrack||function(){(window.visitrack.q=window.visitrack.q||[]).push(arguments)}</script> <script defer data-site="SITE_ID" src="https://visitrack.app/tracker.js"></script>Step 3: Option B — print it from wp_head
Prefer code? Add this to a child theme's
functions.phpor as a PHP snippet. It also prints the one-line queue stub (so inline calls work before the deferred script loads) and skips administrators so your own browsing isn't counted.functions.php// functions.php of a child theme, or a "PHP snippet" in a code-snippets plugin add_action('wp_head', function () { // Optional: don't count logged-in administrators. if (current_user_can('manage_options')) return; echo '<script>window.visitrack=window.visitrack||function(){(window.visitrack.q=window.visitrack.q||[]).push(arguments)}</script>' . "\n"; echo '<script defer data-site="SITE_ID" src="https://visitrack.app/tracker.js"></script>' . "\n"; });Step 4: Clear your page cache
If you use a caching plugin or host-level cache (WP Rocket, LiteSpeed Cache, W3 Total Cache, a managed host's cache), purge it so cached pages pick up the new tag.
How to check VisitTrack is working on WordPress
- Log out (or use a private window — admins are skipped with Option B) and open two pages of your site.
- VisitTrack's live view shows you within seconds; posts and pages appear by path in the Pages tab.
- View source and search for
tracker.js. If it's missing, the cache wasn't purged or the snippet isn't active.
Does VisitTrack track WordPress page navigation?
WordPress pages are full page loads, so each one is a pageview. Paginated archives (/blog/page/2/) have their own paths and are counted separately; query-string variations such as ?replytocom= count toward the same path.
To keep the admin area and login out, nothing extra is needed — the tag is printed on the front end only (wp_head doesn't run in wp-admin). Add data-exclude="/my-account/*" if you also want to skip WooCommerce account pages.
How to track custom events and goals in WordPress
In the block editor, select a Button block, open Advanced in the sidebar, and you can add a CSS class — but not custom attributes. For a button you want to count, use a Custom HTML block with data-vt-goal, or make the button link to a page and create a page goal for that path.
Contact Form 7, WPForms and Gravity Forms submit regular HTML forms, so with automatic events on, each submission records a form_submit event named after the form's id or name. For a cleaner conversion, redirect to a thank-you page and create a page goal for its exact path in Settings → Goals.
<!-- Custom HTML block -->
<a class="wp-element-button" href="/book-a-call/" data-vt-goal="book_call_click">Book a call</a>
<section data-vt-scroll="pricing_viewed">…</section>mailto: and tel: links (common in headers and footers) are recorded as contact_click events automatically — turn that into a goal to count calls and emails.
Revenue attribution on WordPress
WooCommerce payments usually run through gateways that use Stripe PaymentIntents or other processors, which VisitTrack's revenue attribution doesn't read (it attributes Stripe Checkout sessions, Polar, Lemon Squeezy, Paddle and Razorpay — see Revenue attribution). You can still count purchases by source: this hook fires a purchase event on the order-received page, with the order total in its props. It relies on the queue stub included in both options above. If your store uses the block-based order confirmation template, confirm the event fires by adding data-debug to the tag once.
// Fire one "purchase" event on WooCommerce's order-received page.
add_action('woocommerce_thankyou', function ($order_id) {
$order = wc_get_order($order_id);
if (!$order) return;
printf(
'<script>window.visitrack("purchase", %s);</script>',
wp_json_encode([
'amountcents' => (int) round($order->get_total() * 100),
'currency' => $order->get_currency(),
])
);
});Script options you might need on WordPress
All optional — add them to the same tag. Full reference: script configuration.
| Attribute | What it does |
|---|---|
data-cookieless | Store nothing in the browser; the server derives a daily-rotating id. See cookieless mode. |
data-exclude="/app/*" | Never track these paths (comma-separated, * wildcard). Checked on every navigation. |
data-allow-local | Track on localhost and *.local — for testing an install only. |
data-debug | Log every event the script sends, and why it skipped one, to the console. |
data-auto="false" | Turn off automatic events (downloads, contact clicks, form submits, rage clicks, JS errors, 404s). |
WordPress troubleshooting
Visits only counted after visitors click or scroll
A "delay JavaScript execution" option (WP Rocket, LiteSpeed Cache, Perfmatters and others) is holding the script back. Add visitrack.app/tracker.js to its exclusion list.
Nothing tracked behind Cloudflare
Rocket Loader can rewrite third-party scripts. Exclude the tag by adding data-cfasync="false" before its src attribute.
Your consent plugin blocks the script
Plugins like Complianz or CookieYes can auto-block unknown scripts. In standard mode, classify VisitTrack as statistics/analytics; in cookieless mode it stores nothing on the device.
The tag vanished after a theme update
It was added to the parent theme's files. Use a plugin or a child theme instead.
Combined/minified JS broke the install
Exclude tracker.js from your optimizer's JS combining. The tracker reads its settings from its own <script> tag, so it must load as a separate tag with data-site.
WordPress analytics FAQ
Is there a VisitTrack WordPress plugin?
No — and you don't need one. VisitTrack is a single script tag; add it with any header-code plugin such as WPCode, or with a wp_head hook. That means one fewer plugin to update and audit.
How do I add VisitTrack to a WordPress block theme without header.php?
Use a header-code plugin, or hook wp_head from a child theme's functions.php or a code-snippets plugin. Block themes don't have a header.php file, but wp_head still runs on every front-end page.
Does VisitTrack work on WordPress.com?
Yes, on plans that let you install plugins or add custom code. On lower WordPress.com plans you can't add third-party scripts.
How do I exclude myself from WordPress analytics?
Option B above skips logged-in administrators. Otherwise open your site once with ?vt_ignore=1 in the URL, or add your IP under Settings → Exclusions in VisitTrack.
Can VisitTrack track WooCommerce sales?
As purchase events, yes — the woocommerce_thankyou hook above sends one per order with its total, attributed to the visitor's source. WooCommerce payments don't flow into the Revenue tab unless you sell through a supported provider such as Stripe Checkout.
Is VisitTrack a Google Analytics alternative for WordPress?
Yes. It's cookie-free in cookieless mode, so you can drop the consent banner GA4 typically needs in the EU, and it adds revenue attribution and session replays. See VisitTrack vs Google Analytics.
Keep going
- Ghost analyticsAdd VisitTrack to Ghost in Settings → Code injection → Site header (every Ghost(Pro) plan and self-hosted) and count confirmed member signups.
- Google Tag Manager analyticsLoad VisitTrack from Google Tag Manager with a Custom HTML tag on All Pages — SPA-safe, consent-aware, with dataLayer events forwarded as custom events.
- Shopify analyticsAdd VisitTrack to a Shopify store in theme.liquid, track add-to-cart clicks, and send paid orders back as events — with honest notes on checkout limits.
- Cloudflare Pages analyticsAdd VisitTrack on Cloudflare Pages in your HTML or with an HTMLRewriter middleware, exclude it from Rocket Loader, and track AI crawlers at the edge.
- Install the tracking scriptThe reference tag, CSP notes and how to check it's working.
- Custom events and signupsvisitrack(), data-vt-goal, scroll events and server-side signups.
- Use casesHow SaaS teams, indie hackers, stores and agencies use VisitTrack.
- VisitTrack vs Google AnalyticsCookie-free analytics with revenue attribution, compared honestly.
Add VisitTrack to your WordPress site
Cookie-free analytics with revenue attribution, live visitors, funnels and session replays. One script tag, every feature on every plan. 14 days free, no card required.
14-day free trial · No card required · Cookie-free · Cancel anytime
Or explore the live demo first →Not on WordPress? See all 29 integration guides.