Matrix Support Doc

Fix Facebook CAPI Deduplication: Stop Duplicate Events (2026)

Last Updated: July 12, 2026

Question: How do you fix duplicate tracking errors in Meta Ads?

Quick Answer: To fix Facebook CAPI deduplication, pass an identical event_id and an identically-cased event_name from both your browser pixel and your server-side webhook, within a 48-hour window. When Meta receives a matching pair from both sources, it discards the redundant browser payload and records a single, accurate conversion.

Already know you need this fixed and don’t want to hand-build the payload logic? Start with Make.com — it’s the engine every example on this page runs on.

Prefer a visual breakdown?

If you need a full understanding of exactly how the dual tracking trap inflates your ROAS, and how to map the event_id to verify your payloads, watch the architectural teardown from CreatorOpsMatrix below.

Meta Ads Showing Double Conversions? Fix CAPI Deduplication — CreatorOpsMatrix architectural teardown

The ROAS Lie: Why Duplicate Events Kill Campaigns

After debugging broken backend setups for scaling agencies, the diagnosis is consistent: if your Facebook CAPI deduplication is broken, your ROAS is unreliable. You might look at Ads Manager and see a highly profitable campaign, but you are scaling spend based on duplicated conversions. When you double-count purchases, the algorithm optimises against corrupted signals and actively erodes your real margins while reporting fictional returns.

The root cause is almost always the same. When operators migrate to server-side tracking, standard practice dictates running dual tracking — firing the Meta Pixel from the browser while simultaneously firing a server-side webhook from the payment processor. This redundancy is correct architecture. It ensures conversions are recorded even when ad blockers strip the browser pixel. The problem is that executing dual tracking without proper event_id matching gives Meta two separate signals for the same purchase, which it counts as two conversions.

The financial consequence is not just reporting inaccuracy. Meta’s algorithm uses conversion data to optimise ad delivery toward audiences most likely to convert. When your conversion data is doubled, the algorithm learns from a distorted dataset — it over-bids on audiences and creative combinations based on inflated performance signals. Campaigns that appear to be performing at 4x ROAS may be running at 2x in reality. The deduplication error corrupts the optimisation loop, not just the dashboard numbers.

Do not turn off the browser pixel: The pixel captures real-time behavioural signals — button clicks, scroll depth, add-to-cart events — that server-side tracking cannot observe. CAPI is the failsafe that guarantees conversion recording when the pixel is blocked. Both are required. Proper event_id matching is what prevents the double count, not disabling one of the two streams.

The Core Mechanism: How event_id Deduplication Works

According to Meta’s official Conversions API deduplication documentation, the Graph API relies on a primary matching variable called the event_id. When both the browser pixel payload and the server-side CAPI payload carry an identical event_id string, Meta’s deduplication engine recognises them as the same event and discards the redundant signal, recording a single accurate conversion.

Without an explicit event_id in both payloads, Meta falls back to attempting deduplication via fbc and fbp cookie parameters combined with IP address matching. This fallback is unreliable — it fails entirely for users on VPNs, users who have cleared cookies, users in cross-device journeys, and users whose browsers block first-party cookie storage. The event_id is the only deterministic deduplication signal.

The Two Rules Most Setups Get Wrong

There are exactly two conditions Meta checks, and both have to pass. Most broken setups pass one and silently fail the other.

  • The event_id string must match byte-for-byte. A trailing space, a different casing convention, or a truncated string breaks the match with no error thrown — the events simply never merge.
  • The event_name must match exactly, including capitalization. A Pixel event fired as Purchase will not deduplicate against a CAPI event sent as purchase. Meta treats these as two distinct event types, so even a perfect event_id match will not save you if the names don’t agree.

Both events also have to land inside Meta’s 48-hour deduplication window. If your server-side event fires more than 48 hours after the browser event carrying the same event_id, Meta no longer merges them — both get counted. In practice this only bites you on delayed-fulfillment flows (offline sales synced later, backorder confirmations), but it’s worth checking if your CAPI events are queued rather than sent in real time.

🌐
Path A: Browser Pixel
Sends “Purchase” + event_id: “txn_888”
⚙️
Path B: Server CAPI
Sends “Purchase” + event_id: “txn_888”
🛡️
Meta Deduplication Engine
Matches “txn_888” + “Purchase” across both payloads within 48 hours. Discards Path A browser signal. Records 1 accurate conversion.

Implementation: The Exact Code for event_id Matching

The event_id must be generated once per conversion event and passed to both the browser pixel and the server-side API payload simultaneously. The value can be any unique string — a transaction ID from your payment processor, a UUID generated at checkout initiation, or a timestamp-based hash. The only requirement is that both payloads carry the exact same string with no variation in casing or formatting, and the same event_name.

1. The Browser Pixel Payload (JavaScript)

fbq('track', 'Purchase', {
  value: 100.00,
  currency: 'USD'
}, {
  eventID: 'txn_12345'
});

2. The Server-Side CAPI Payload (JSON)

{
  "data": [
    {
      "event_name": "Purchase",
      "event_time": 1715000000,
      "action_source": "website",
      "event_id": "txn_12345",
      "user_data": {
        "em": ["HASHED_EMAIL_SHA256"],
        "ph": ["HASHED_PHONE_SHA256"],
        "fbc": "fb.1.1715000000.AbCdEfGhIjKlMnOp",
        "fbp": "fb.1.1714000000.1234567890"
      },
      "custom_data": {
        "value": 100.00,
        "currency": "USD"
      }
    }
  ]
}

Note that event_name is "Purchase" in both payloads above, matching the Pixel’s 'Purchase' string exactly. This is the detail that breaks silently. The server payload also includes the user_data object with hashed email and phone fields, required for Event Match Quality scoring — see the full EMQ optimisation guide for the correct SHA-256 normalisation sequence. The fbc and fbp parameters come from the browser cookies set by the Meta pixel and should also be passed server-side when available to maximise match rates.

What Event_id Values Are Valid

SourceExample ValueNotes
Stripe Charge IDch_3PxxxxxxxxxxxxxUnique per transaction, available in webhook payload
UUID v4f47ac10b-58cc-4372-a567Generate at checkout initiation, store in session
Timestamp + User ID hash1715000000_usr_8821Deterministic, reproducible from server logs
Order Numberorder_20260508_4421Only valid if orders are never duplicated in your system

Diagnosing 0% Event Coverage

Operators implementing dual tracking frequently check their Events Manager after deployment and find a 0% Event Coverage warning next to their Purchase event. This warning has a specific meaning: Meta is receiving your server-side CAPI events but cannot find any browser pixel events to match them against. The server stream is working. The browser stream is broken, absent, or firing against stale data.

The standard engineering causes of 0% event coverage are:

  • Asynchronous Loading Conflict: If your pixel loads via Google Tag Manager and the event_id is generated by a separate script, the pixel may fire before the ID is available, sending a null eventID value to Meta. The pixel fires successfully but without a deduplication key, making it impossible for Meta to match it to the server event.
  • Performance Plugin Deferral: WordPress optimisation plugins routinely defer JavaScript execution to improve page load scores. If they defer your Meta pixel script, the browser event fires after the user has already left the purchase confirmation page, or does not fire at all.
  • Stale Server Cache: If you enable CAPI on a live site without purging the server-side page cache, cached checkout confirmation pages keep serving the pre-CAPI pixel snippet. The server sends events correctly; the browser is silently running outdated code. Clearing the full-page cache after any CAPI configuration change resolves this immediately.
  • Hosted Payment Gateway: If your checkout redirects to a third-party payment page and the user does not return to a confirmed Thank You page on your domain, the pixel has no page environment to fire in. The server catches the payment webhook but no browser event is recorded.
  • Ad Blocker Rate: In audiences with high technical literacy — developers, SaaS operators, security professionals — ad blocker penetration can exceed 40%. If your audience skews technical, a meaningful percentage of browser events will never fire regardless of implementation quality, resulting in a non-zero but below-par coverage score.

Use the Test Server Events Tool First

Do not wait for live traffic to verify your deduplication setup. Open Meta Events Manager, navigate to your pixel, click Test Events, and trigger a live purchase using a Stripe test card. Verify that the server event indicator appears alongside the browser event indicator with the exact same event_id string and event_name, and that the total event count shows 1 — not 2. This single verification step confirms deduplication is functioning before you scale spend.

⚙️

Debugging this by hand eats hours you don’t have. The webhook catcher, PII hashing, and event_id/event_name matching logic are already built and tested in production.

Start with Make.com →

Recommended CAPI Stack for 2026

To avoid building custom API routing from scratch and risking implementation errors that break deduplication silently, standardise your execution stack across these three layers. The combination covers pixel firing, server-side routing, and managed attribution without redundant tooling.

  • Make.com: The primary logic engine for catching Stripe or Shopify payment webhooks, extracting the transaction ID as the event_id, normalising and hashing customer PII, and routing the structured JSON payload to the Meta Graph API endpoint.
  • GTM Server-Side: For operators requiring Google Analytics 4 event routing alongside Meta, a server-side GTM container allows a single server-side tag to distribute event data to multiple ad platforms without duplicate frontend pixel implementations.
  • Managed Attribution: If your team lacks the engineering bandwidth to maintain custom webhook routing, a managed attribution platform handles the server-side connection automatically. Review the Hyros alternative guide for a cost comparison between managed and self-built attribution infrastructure.

After Deduplication: Low EMQ Scores

Fixing deduplication resolves the double-counting problem but does not automatically improve Event Match Quality. EMQ scores measure how well Meta can match your server-side events to real Facebook user profiles. A score below 6.0 out of 10.0 means a significant proportion of your server events are landing without being attributed to a known user — reducing the optimisation value of the server-side data.

Low EMQ after fixing deduplication almost always indicates a PII normalisation error. Email addresses passed to the Meta API must be lowercased and stripped of whitespace before SHA-256 hashing. Phone numbers must include the country code prefix and contain only digits. If your Make.com scenario is hashing raw email values without normalising them first, the hashes will not match Meta’s stored user data even when the underlying email address is correct. The full normalisation and hashing sequence is documented in the Facebook CAPI match quality optimisation guide.

Related Attribution Guides

Frequently Asked Questions

Why do I have duplicate tracking errors in Meta Ads?

Duplicate tracking errors occur when you send data from both the browser pixel and the Conversions API without a matching event_id and event_name in both payloads. Without both matching, Meta has no way to recognise that both signals represent the same conversion event and counts each one independently, inflating your reported purchase volume and corrupting your ROAS data.

What causes 0% event coverage in Meta Events Manager?

A 0% event coverage warning means Meta is receiving your server-side CAPI events but cannot find any corresponding browser pixel events to match against. The server stream is working correctly. The browser pixel is either misconfigured, deferred by a performance plugin, blocked by an ad blocker, serving from a stale server cache, or has no page environment to fire in due to a hosted payment gateway redirect.

What is the Facebook CAPI deduplication window?

Meta’s deduplication window for matching Pixel and CAPI events is 48 hours. If the server-side event for a given event_id fires more than 48 hours after the browser event, Meta will not merge them and both get counted. Server-side events should fire within seconds of the browser event whenever possible.

Does event_name have to match exactly between Pixel and CAPI?

Yes, and this is the most common silent failure. Meta treats event_name as case-sensitive. A Pixel event named Purchase will not deduplicate against a CAPI event named purchase, even with an identical event_id. Both values must match character-for-character.

How does the event_id parameter work for deduplication?

The event_id is a unique string generated at the moment of conversion — typically a transaction ID, UUID, or order number. Both the browser pixel payload and the server CAPI payload carry this same string, alongside a matching event_name. When Meta’s deduplication engine receives two events with identical values on both fields within the 48-hour window, it merges them into a single conversion and discards the redundant signal.

Can Facebook deduplicate without event_id?

Meta attempts to match events using fbc and fbp cookie parameters and IP address signals when event_id is absent. This fallback fails for VPN users, users with cleared cookies, cross-device journeys, and browsers that block first-party cookie storage. Explicitly passing a matching event_id is the only deterministic method to prevent duplicate conversion counting across all user scenarios.

How long does Facebook CAPI deduplication take?

Meta’s deduplication engine processes events in near real-time as they arrive at the Graph API endpoint. The Events Manager dashboard, however, operates on a reporting delay and can take 20 to 30 minutes to update the deduplication charts and event coverage metrics. Use the Test Events tool for immediate verification rather than waiting for the dashboard to refresh during implementation.

Should you turn off the browser pixel and rely only on CAPI?

No. The browser pixel captures real-time behavioural data — page views, button clicks, add-to-cart events, scroll depth — that server-side tracking cannot observe because these signals occur in the browser before any server interaction happens. CAPI acts as the attribution failsafe that guarantees purchase conversion recording when the pixel is blocked. Running both with proper event_id and event_name matching is the correct architecture.

What should you do after fixing deduplication if EMQ scores are still low?

Low Event Match Quality after fixing deduplication indicates a PII normalisation error in your server payload. Email addresses must be lowercased and stripped of whitespace before SHA-256 hashing. Phone numbers must include the country code prefix and contain only digits with no spaces or formatting characters. If your Make.com scenario hashes raw values without normalising them first, the resulting hashes will not match Meta’s stored user data even when the underlying contact information is correct.

Automate Your CAPI Infrastructure

Stop debugging raw JSON payloads manually. Deploy the complete pre-built Make.com architecture that handles webhook catching, PII hashing, event_id/event_name matching, and Meta Graph API routing in one scenario.

Start Building on Make.com →

Includes the exact scenario file used to build every example in this guide.

♟️

The Architect — CreatorOpsMatrix

The Architect is a technical infrastructure engineer focused on server-side attribution, Make.com API routing, and Meta Conversions API architecture. CreatorOpsMatrix publishes production-tested automation blueprints for scaling agencies and SaaS operators.

Transparency Protocol: CreatorOpsMatrix operates as an independent technical research hub evaluating workflow automation software. Make.com and Hyros-related links across this domain are partner affiliate links. If you build your infrastructure using these routes, we earn a commission at zero additional cost to you. We only document tools we have actively tested in production environments.
Operator Responsibility: The JSON payload structures, API routing schemas, and implementation sequences documented across CreatorOpsMatrix are strictly for educational and informational purposes. Meta’s API specifications, deduplication behaviour, and Events Manager interface are subject to change. You are solely responsible for testing, validating, and maintaining your attribution infrastructure in your own production environment.

Scroll to Top