Server-side tracking recovers some data, but it still leaves massive gaps when browsers block the request or users decline consent. Combine server-side tracking with offline conversion tracking to feed GA4, Google Ads, and Meta the absolute truth from your backend.
Free, recorded Loom audit of your setup. Delivered in 48 hours. No sales call.
// Recorded on a live store with server-side GTM already running
We map your pipeline and send the findings within 48 hours.
"Bipin found 4 critical errors we had no idea about. Our Facebook ROAS went from 1.4x to 3.6x in 6 weeks."
Your audit is in the queue. We'll compare what your backend knows against what your ad platforms report, and send a personal Loom video within 48 hours.
Watch the 7 minute test where ad blockers kill a live server-side request, and the backend recovers the same purchase with UTM and GCLID intact.
Proof From a Live Account
One live store. Three conversion actions running in parallel over the same three days: server-side only, offline only, and both combined. Same traffic, same orders. Here is the raw Google Ads report.
// Tap the image to enlarge
The Three Rows, Side by Side
A fully working server-side GTM setup. This is the number most stores believe is the truth.
Orders pushed from the backend through the Data Manager API. On its own it already sees almost as much as the full server-side setup.
Both sources feeding one conversion action, deduplicated by transaction ID. This is what the bidding algorithm should be learning from.
90.40 conversions were deduplicated away because the tag and the backend upload carried the same transaction ID. Google kept one record per order and used the backend value. What is left over — the 62.60 — are orders that only the backend ever knew about.
// Reported conversions keep rising after the fact. How to read these windows correctly →
And Google Rates the Setup Itself
// Live client account. Account name and value currency removed. Google Ads reports fractional conversions under data-driven attribution, and records them against the original click date, so recent windows continue to fill in.
Your gap will be a different number. It is never zero, and you cannot see it from inside Google Ads — it only shows up when backend orders are compared against what the platforms reported.
Show Me My GapThe Problem
Server-side GTM is a massive upgrade from client-side pixels, but it is not a magic bullet. It is still limited by browser restrictions and user behavior. If you stop at server-side, you are still missing 20 to 25% of your actual conversions.
If a user rejects advertising cookies, server-side tracking legally cannot fire. The conversion happens on the backend, but the ad platform never sees it.
Safari caps JavaScript cookies at 7 days (or 24 hours if a click ID is present). Server-side can't fix a browser-level block that deletes the identifier before the conversion happens.
Advanced ad blockers block the server-side endpoints themselves, and strip UTM parameters and click IDs out of the landing page URL. If the request never leaves the browser, your server never processes it.
A user clicks an ad on mobile, but buys on desktop a week later. The tracking link is broken, and server-side tracking alone can't stitch that journey together.
Live Proof
This is not a slide deck. It is a recorded test on a live store that already has server-side GTM running through Stape. Ad blockers and Brave Shields get switched on one at a time until the purchase disappears from both Google and Meta, then the backend feed recovers the same order with the campaign data intact.
// Tap a chapter to jump straight to that moment
What the test shows
Page loads with UTM parameters and a GCLID on the URL. The server container receives the event and forwards it to Google and Meta. Nothing is broken yet.
uBlock, AdGuard, and Adblock Plus are enabled one by one. The data still arrives. This is the point where most setups get signed off as healthy.
With an advanced blocker plus Brave Shields, the UTM parameters are removed from the URL, the GCLID is truncated, and the request to the server container never leaves the browser. The server container stays empty.
The test order goes through checkout and completes. Revenue is in the store admin. Google and Meta received nothing at all, so bidding never learns from that sale.
The store backend fires the purchase as an offline conversion with order data and hashed customer info, using the transaction ID as the event ID so the platforms can deduplicate it.
Because backup parameters were written server side before the blocker could strip them, the source, medium, campaign, and GCLID are all restored on the recovered conversion. Not just a sale, a properly attributed sale.
Every store leaks a different amount. The only way to know yours is to compare backend orders against what Google and Meta actually reported, which is exactly what the free audit does.
The Solution
Server-side tracking captures what the browser allows. Offline conversion tracking pushes the absolute truth from your CRM or backend directly into GA4, Google Ads, and Meta.
If an ad blocker or consent banner stopped the browser tag from firing, your backend still knows the sale happened. Offline conversion tracking pushes that backend truth to the ad platforms, filling in the missing pieces.
This creates a closed-loop system where Google and Meta learn from actual outcomes (real sales, real leads, real margins) rather than just pixel noise. This is how you achieve 100% data accuracy.
Push real outcomes from your CRM/ERP to ad platforms, recovering the 20 to 35% of conversions lost to ITP, consent, and ad blockers.
When platforms learn from actual CRM deal values and real margins instead of flat revenue, tROAS and Smart Bidding finally optimize for profit.
Hashed customer data reaches ad platforms without exposing raw PII, keeping you GDPR and CCPA aligned while maintaining accuracy.
The part most setups skip
Recovering the sale is only half the job. If the click ID and campaign data were stripped from the URL, the recovered conversion lands as unattributed and your reports still lie. We write a mirrored copy of the click ID, source, medium, and campaign at the first server-side touch, before the blocker can remove them, then attach that copy to the offline upload. That is why the recovered order in the video still carries its full campaign path.
No Double Counting
A common fear of running both server-side and offline tracking is inflating conversions. Don't worry. Google and Meta have built-in deduplication logic to ensure a single purchase is never counted twice.
The rule everything else depends on
This is the single detail that decides whether combining server-side and offline tracking gives you accuracy or garbage. Deduplication only happens inside one conversion action. Send the tag to one action and the backend import to a second one, and there is nothing for the platform to match against — it cannot tell a recovered order from a duplicate, because it never compares the two.
transaction_id (your order ID).event_id, inside the 48-hour window. A separate offline event set has nothing to deduplicate against.transaction_id present on both the tag event and the imported one.It is also why the report earlier on this page reads 223.36 and not 313.76, and why Google's diagnostic describes it as one conversion action fully optimised using tag and imported data. One action. Two sources. That is the whole trick.
Rule: Connect your backend feed to the existing web conversion action, never a new one. Google uses the Transaction ID (Order ID) to match them.
If the tag was blocked (no match), Google counts the CRM upload as a new (recovered) conversion.
Rule: Both the browser/server-side tag and the offline CRM feed must send the exact same Event ID and Event Name (e.g., 'Purchase'). Meta matches them within a 48-hour window.
If the window closes before the CRM uploads, it counts as two. Upload backend data as quickly as possible.
This is the exact behaviour shown at , where the transaction ID is reused as the Meta event ID and the recovered purchase is accepted without duplicating anything.
And it is what the account numbers prove: 160.76 + 153.00 raw conversions became 223.36 recorded, not 313.76. See the account data.
FAQ
Reading Your Numbers After Go-Live
So do not judge a campaign on last week. The honest read is a 30-day window compared against the same length of period before it, with the most recent stretch excluded — Google's guidance is to wait until your average days to conversion have passed, which you can look up in the Path metrics attribution report under “Avg. days to conversion.” Their example uses 14 days; yours may be shorter or much longer. The three-day window shown earlier on this page was still filling in when the screenshot was taken, which makes +38.9% the conservative reading, not the optimistic one.
// Sources: Google Ads Help — Best practices for managing attribution model changes; Guidelines for importing offline conversions; Fix discrepancies and errors in offline conversion imports; About modelled online conversions; Data discrepancies: factors and troubleshooting.