Most WordPress marketing attribution setups are broken in at least one place, and most businesses do not know it. The tracking code is installed, the forms are submitting, leads are showing up in the CRM — but the lead source fields are blank, or the campaign data is wrong, or Google Ads is optimizing toward the wrong conversions. The setup looks like it is working until you try to use the data and realize you cannot trust it.
This guide walks through every layer of a WordPress attribution stack, how to test each one, and what to look for when something is wrong. Run through this checklist when you are setting up attribution for the first time, when you inherit a site with existing tracking, or when you suspect your data has drifted from reality.
Layer 1: UTM Parameter Capture
UTM capture is the foundation. If it breaks, every layer above it is also broken — forms submit without source data, CRM contacts have no attribution, and Google Ads reports show only blank or direct traffic.
How to test it:
- Build a test URL with UTM parameters: append
?utm_source=test&utm_medium=audit&utm_campaign=attribution-checkto any page on your site. - Open the URL in an incognito window. Navigate to a second page on the site (like the contact page) without the UTM parameters in the URL.
- Open browser developer tools, go to Application, and look for cookies. You should see cookies named something like
utm_source,utm_medium,utm_campaign(the exact names depend on how your capture script is written) with the values from step 1. - If the cookies are present after navigating away from the original UTM URL, capture is working. If the cookies disappear when you navigate away, the script is running on page load rather than storing to persistent cookies — this means cross-page attribution is broken.
Common failure modes:
- Script only reads UTMs on the landing page and passes them directly to a form hidden field without storing to cookies — breaks when the visitor browses to a different page before submitting
- Cookie expiration set to session only — the UTM data disappears when the browser closes, losing attribution for visitors who return days later
- Script fires after the page load event fires, missing UTMs if the visitor navigates away very quickly
- UTM parameters getting stripped by a redirect on the landing page — check whether any redirect (www to non-www, HTTP to HTTPS, trailing slash canonicalization) removes query parameters
Layer 2: Hidden Form Fields
Hidden fields read the UTM cookies at form submission and pass them to your CRM or email system. If the fields are configured but empty on submission, the UTM capture is failing. If the fields do not exist, attribution data never reaches the CRM.
How to test it:
- Build a test URL with UTM parameters as in Layer 1.
- Open the URL in an incognito window and navigate to a page with a form.
- Open developer tools and look at the form in the Elements tab. Find the hidden input fields — they should have names matching your UTM parameters (utm_source, utm_campaign, etc.) and values populated from the cookies.
- If the hidden fields are present but empty, the script reading cookies into fields is not running. If the hidden fields are not present at all, the form setup is incomplete.
- Submit a test form and check the submission in your CRM or form submission log. The UTM fields should appear with the test values you set in step 1.
Common failure modes:
- Hidden fields added to the form but the script reading cookies into them is missing or not loading
- Script runs before the form renders, so the hidden fields do not exist when the script tries to populate them — usually fixed by deferring the script or moving it to after the form HTML
- Form uses AJAX submission that bypasses the hidden field population script
- Multiple forms on the same site with the hidden fields added to only some of them
Layer 3: Form-to-CRM Connection
This layer routes the form submission into your CRM with all fields intact, including the attribution fields. A broken connection here means leads still get captured somewhere (email inbox, form plugin database) but never reach the CRM with their source data.
How to test it:
- Submit a test form using the UTM test URL from Layer 1. Use a name and email address you control so you can find the submission.
- Check your CRM immediately after submission. Look for the test contact and inspect their properties. You should see Lead Source, Lead Campaign, Lead Medium (or whatever custom properties you created) populated with the values from your UTM test.
- If the contact appears but the attribution fields are blank, the form-to-CRM mapping is missing the custom field connections. If the contact does not appear at all, the connection itself is broken.
Common failure modes:
- Form plugin updated and the native CRM integration add-on stopped working — check the plugin’s integration settings page for errors
- CRM API key expired or revoked
- Custom attribution properties exist in the CRM but the field mapping in the form plugin was not updated to include them
- Webhook URL changed (CRM rotated an endpoint) and the form plugin is still sending to the old URL
- Form submissions going to a Zapier trigger that stopped working — check Zapier task history for failures
Layer 4: Google Analytics 4 Conversion Tracking
GA4 should record a conversion event when a form is submitted or when a visitor reaches a thank-you page. If this is broken, GA4 reports show zero conversions, and you cannot use GA4 for channel-level attribution.
How to test it:
- Install the Google Analytics Debugger Chrome extension, or use GA4’s DebugView (in GA4 Admin > DebugView).
- Submit a test form on your site while DebugView is active. You should see an event fire with the name you configured (form_submit, generate_lead, or a custom event name).
- In GA4 under Reports > Conversions, check that the conversion action has recorded at least one conversion. Allow up to 24 hours for conversions to appear in standard reports, but DebugView shows events in real time.
Common failure modes:
- GA4 tracking code installed but the conversion event trigger in Google Tag Manager was not set up or is misconfigured
- Thank-you page redirect is not actually loading the thank-you page URL — if a form submits via AJAX and shows a success message without a page redirect, a thank-you page trigger never fires
- Form plugin’s built-in conversion event fires but Google Tag Manager is configured to fire a duplicate event, creating double-counted conversions
- GA4 property was switched but Google Tag Manager still has the old Measurement ID
Layer 5: Google Ads Conversion Import
Google Ads needs to receive conversion signals to optimize campaign bidding. If GA4 conversions are not imported into Google Ads, or if the import is set up but not matching, the Google Ads account is flying blind on which clicks produce leads.
How to test it:
- In Google Ads, go to Goals > Conversions. Find your imported conversions and check the “Status” column. It should show “Recording conversions” and have recent conversion data. “No recent conversions” with a recent campaign spend is a red flag.
- Check the conversion window setting. If it is set to 30 days and your sales cycle is longer, conversions are being cut off before the deal closes.
- In Google Ads under Diagnostics > Conversion tracking diagnostics, check for warnings about unverified conversions or tags not firing.
Common failure modes:
- GA4 conversion is configured but the import link between GA4 and Google Ads is not set up under Tools > Linked accounts
- Multiple conversion actions counting the same event — inflates conversion numbers and confuses bidding
- Auto-tagging is disabled in Google Ads settings — gclid values do not get appended to ad click URLs, so GA4 cannot attribute sessions to specific ads
- Conversion action marked as “Don’t use for bidding” when it should be the primary bidding signal
Layer 6: CRM Deal Attribution
This is the final layer that most setups never reach. It connects closed revenue in the CRM back to the channels and campaigns that produced it. If this is missing, you can count leads by source but cannot answer which sources produce paying customers.
How to test it:
- Find five to ten recently closed deals in your CRM. Open each contact record and look for the attribution custom properties (Lead Source, Lead Campaign, etc.).
- If the properties are blank on most records, the hidden field population is failing at submission — go back to Layer 2.
- If the contact record has attribution but the deal record does not, the attribution properties are not being copied to the deal object at deal creation — this requires a workflow or field duplication setup in your CRM.
- Run a simple report: closed deals grouped by Lead Source Medium (cpc, organic, email, direct). If everything shows as blank or direct, attribution is broken at the contact level.
Common failure modes:
- Attribution properties exist on the Contact object but not on the Deal object — deal-level reporting cannot filter by source
- CRM workflow that was supposed to copy source properties from contact to deal was disabled or never created
- Lead source field getting overwritten on repeat form submissions — if a contact submits twice and the second submission has different UTMs, the original source is lost
Running the Full Audit
Work through these layers in order. Each layer depends on the one below it — if UTM capture is broken, everything above it is also broken, so fix from the bottom up. The most common pattern in broken setups is that the visible parts look fine (forms submit, leads appear in the CRM) but the invisible parts (UTM cookie storage, hidden field population, CRM field mapping) have a gap that silently drops attribution data.
Run a fresh test submission after fixing each layer before moving to the next one. A single test that passes through the whole stack end-to-end — UTM in the URL, form submission, contact in CRM with attribution fields, conversion recorded in GA4 and Google Ads — is the only confirmation that the full stack is working.
For a WordPress attribution setup where each of these layers is integrated and tested as part of the installation — so you do not inherit a partially working stack and discover the gaps six months later when you try to run a channel report — Sales Provenance handles UTM capture, hidden field population, CRM routing, and Google Ads conversion tracking as a connected system. Related reading: UTM parameter tracking on WordPress, Google Tag Manager for WordPress, CRM integration for WordPress, and Google Ads conversion tracking for WordPress.