Meta Conversions API Setup Nepal: CAPI and GA4 Guide
Meta Conversions API (CAPI) sends conversion events from your server to Meta, alongside the browser Pixel. For Nepali e-commerce, getting CAPI and GA4 events right matters more than in most markets, because so many orders pass through a wallet redirect, close on WhatsApp or are paid in cash on delivery, and those are exactly the places where browser tracking breaks.
This guide covers why Pixel data goes missing, the four ways to set up CAPI, a Meta-to-GA4 event map, deduplication, customer data and hashing, Nepal-specific fixes for COD, eSewa/Khalti and WhatsApp orders, consent, testing and troubleshooting.
→ CAPI dictionary · Meta Pixel · Facebook Ads Nepal
Why browser Pixel data goes missing
The Pixel runs in the visitor’s browser, so anything that stops scripts, cookies or page loads also stops the event:
- Safari’s Intelligent Tracking Prevention blocks third-party cookies by default and deletes cookies set by JavaScript after seven days of Safari use without interaction with the site (WebKit). The Pixel’s own browser cookie is set by script, so returning iPhone and Mac visitors are harder to connect to earlier ad clicks.
- iOS App Tracking Transparency requires apps, including Facebook and Instagram, to ask permission before tracking users across other companies’ apps and websites (Apple Developer). Many users decline, which limits what Meta can link from in-app browsing.
- Ad blockers and privacy extensions commonly block the Pixel script.
- Consent choices mean some visitors should not be tracked at all.
- Nepal-specific breaks: wallet redirects that never return to the thank-you page, slow 4G connections that close before the tag fires, and sales that finish on WhatsApp or at the door.
CAPI recovers events lost to technical breaks. It is not a way around consent or ATT; send only what your privacy notice and the user’s choices allow.
How Pixel and CAPI work together
Customer completes an order
├── Browser: Pixel sends Purchase (eventID: order_10482)
└── Server: CAPI sends Purchase (event_id: order_10482)
→ Meta matches the pair and counts one purchase
The browser copy is fast and carries browser context; the server copy is reliable and can carry more customer data. Meta keeps one of them when the event name and ID match.
Choose a setup path
| Path | What you need | Best for |
|---|---|---|
| Partner integration | Shopify’s Facebook & Instagram app, or Meta’s official plugin for WooCommerce; admin access to the store and Meta business portfolio | Stores on those platforms that want the quickest route |
| Conversions API Gateway | Meta’s no-code gateway, deployed from Events Manager into your own cloud account (you pay the hosting) | Sites with a working Pixel and no developer |
| Server-side Google Tag Manager | A server container (Google Cloud or a managed host), a first-party subdomain, a data layer and someone comfortable with GTM | Sites that also want server-side GA4 and Google Ads |
| Direct API | A developer, the dataset (Pixel) ID and an access token generated in Events Manager | Custom platforms, apps, CRMs and offline sales |
Points to note:
- Partner integrations handle deduplication for you, but check in Events Manager which customer parameters they actually send.
- The Gateway forwards what the Pixel sees. It helps when the browser fires but the request is blocked on its way to Meta; it cannot recover a purchase the browser never recorded, such as a wallet payment where the customer never returned to your site.
- Server-side GTM lets one data layer feed GA4, Google Ads and Meta. See GA4 server-side tracking in Nepal and the GA4 and GTM recipes.
- Direct API is the only path that sends events triggered by your order system, which is what COD and WhatsApp orders need. Low-code tools can do this too; see the n8n Meta API guide.
Event mapping: Meta standard events and GA4 e-commerce events
Use one data layer push per action and map it to both platforms. GA4’s recommended e-commerce events are documented in the Google Analytics developer guide.
| Customer action | Meta standard event | GA4 recommended event | Meta parameters | GA4 parameters |
|---|---|---|---|---|
| Views a product | ViewContent |
view_item |
content_ids, content_type, value, currency
|
currency, value, items[]
|
| Adds to cart | AddToCart |
add_to_cart |
content_ids, contents, value, currency
|
currency, value, items[]
|
| Starts checkout | InitiateCheckout |
begin_checkout |
content_ids, num_items, value, currency
|
currency, value, coupon, items[]
|
| Chooses payment method | AddPaymentInfo |
add_payment_info |
value, currency
|
currency, value, payment_type, items[]
|
| Completes the order | Purchase |
purchase |
value, currency, content_ids, contents, order_id
|
transaction_id, currency, value, shipping, items[]
|
| Submits a lead form | Lead |
generate_lead |
value, currency (optional) |
currency, value (optional) |
Each GA4 items[] entry should carry at least item_id or item_name, plus price and quantity. Always send currency: 'NPR' with any value, and keep the product IDs identical across Meta and GA4 so reports reconcile.
A purchase push might look like this:
dataLayer.push({ ecommerce: null });
dataLayer.push({
event: 'purchase',
event_id: 'order_10482',
ecommerce: {
transaction_id: '10482',
value: 4850,
currency: 'NPR',
payment_type: 'esewa',
items: [
{ item_id: 'KRT-022', item_name: 'Kurta set', price: 4850, quantity: 1 },
],
},
});
payment_type is a GA4 parameter on add_payment_info; storing it on the order as well lets you compare COD and wallet orders later.
Deduplication with event_id
Meta deduplicates a browser and a server event when the Pixel’s eventID equals the server’s event_id and the event names match exactly, provided the second copy arrives within 48 hours of the first. Purchase and purchase are different names, and an ID with a stray prefix will not match.
- Generate the ID once, from the order or lead ID, and pass it to both the Pixel and the server.
- Use a different ID for each event instance; reusing one ID for many orders discards real purchases.
- GA4 deduplicates
purchaseevents with the sametransaction_idon web streams (Analytics Help). Never send an empty transaction ID: GA4 treats all empty IDs as the same transaction. - If you send GA4 purchases from both the browser and the server, pick one as the source of truth. Mixed setups can still double count.
Customer information parameters and hashing
Matching depends on the customer data sent with each event. Meta requires most of it to be normalised and hashed with SHA-256 before it leaves your server; the Pixel hashes automatically when you use advanced matching.
| Parameter | Normalise before hashing | Hash? |
|---|---|---|
em (email) |
Trim spaces, lowercase | SHA-256 |
ph (phone) |
Digits only with country code, no +, spaces or leading zeros: 97798XXXXXXXX
|
SHA-256 |
fn, ln (name) |
Lowercase, no punctuation | SHA-256 |
ct (city) |
Lowercase, no spaces or punctuation: kathmandu
|
SHA-256 |
country |
Two-letter ISO code, lowercase: np
|
SHA-256 |
external_id |
Your stable customer ID | Recommended |
client_ip_address, client_user_agent
|
As received by your server | Do not hash |
fbp, fbc
|
The _fbp cookie and the click ID cookie or fbclid value |
Do not hash |
Store fbp and fbc with the order at checkout. When a COD order is confirmed days later, those values let the server event connect back to the ad click.
Event Match Quality
Events Manager shows an Event Match Quality score from 0 to 10 for each web event, based on the customer information you send and how much of it matches Meta accounts. Meta does not publish one target that suits every business; Purchase usually scores higher than AddToCart because more customer data exists at that point. Track the score per event and improve it by adding email, phone, external_id, fbp and fbc where consent allows.
Nepal specifics
Cash on delivery
COD inflates conversions if every placed order counts as a sale. Choose one approach and document it:
-
Purchase on confirmation or delivery (recommended for high-return categories). Fire
InitiateCheckoutand a custom event such asOrderPlacedin the browser. SendPurchasefrom the server when the order is phone-confirmed or delivered, with the stored customer data,fbpandfbc. Bidding then learns from real sales. -
Purchase on order, with corrections. Fire
Purchaseat order placement for a faster signal, and report delivered revenue separately in GA4 and your back office. Simpler, but Meta’s reported results will run ahead of real sales.
Meta retired its separate Offline Conversions API in 2025. Offline and CRM outcomes, such as in-store sales or orders confirmed by your team, are now sent through the Conversions API to your dataset with an action_source such as physical_store or system_generated. Meta’s developer documentation could not be fetched directly while this guide was updated, so check the current action_source values and time limits there before you build. Events from websites must be sent within seven days of the time they happened.
For the CRM and offline side in Google Ads, see UTM and offline conversions for WhatsApp sales.
eSewa, Khalti and other wallet redirects
Wallet checkouts send the customer to the wallet and back. Three things go wrong:
-
Double firing. The success callback and the thank-you page both fire
Purchase, or the customer reloads the page. Fix: use the order ID as both the Metaevent_idand the GA4transaction_id, and fire the server event only after your backend has verified the payment with the wallet. - Missing purchases. The customer pays but never returns to your site. Only a server event triggered by payment verification catches these.
- Lost source. The return from the wallet domain starts a new session attributed to the wallet. Add the wallet and gateway domains to List unwanted referrals in GA4’s tag settings.
The eSewa, Khalti and Fonepay gateway guide covers the integrations themselves.
WhatsApp orders
Many Nepali stores take the order in chat. Options, from simplest:
- Log each WhatsApp order in your order sheet or CRM with the phone number and the ad or UTM that started the chat, then send confirmed orders server-side.
- If you run click-to-WhatsApp ads through the WhatsApp Business Platform (API), Meta’s Conversions API for business messaging can attribute a purchase to the ad using the click ID captured when the chat starts. It needs API access through Meta or a provider; the WhatsApp Business app alone cannot send these events.
Consent
- Show a consent banner where required and record choices.
- Use Consent Mode v2 for Google tags so GA4 and Google Ads respect each visitor’s choice.
- The Meta Pixel supports consent calls (
fbq('consent', 'revoke')andfbq('consent', 'grant')); wire them to your banner. - On the server, send hashed customer data only when your privacy notice covers advertising use. Nepal’s Individual Privacy Act, 2075 requires consent when collecting personal data and limits use to the stated purpose; see the first-party data strategy guide.
Testing
-
Meta Test Events. In Events Manager, open Test Events. Browse the site to see Pixel events; add the
test_event_codeto server payloads to see CAPI events in the same view. Confirm each event shows as deduplicated with matching IDs. -
GA4 DebugView. Use Tag Assistant or
debug_modeand check that each e-commerce event arrives once withcurrency,valueanditems. - Wallet test. Pay a small amount with eSewa or Khalti, reload the thank-you page twice, and confirm one purchase in both tools.
-
COD test. Place a COD order, confirm it in the back office, and check that
Purchasearrives only at confirmation. - Reconcile weekly. Compare Meta, GA4 and your order system for the same week. Small gaps are normal because of attribution windows and consent; large or growing gaps point to a broken tag.
Troubleshooting
| Symptom | Likely cause | Fix |
|---|---|---|
| Purchases roughly double in Ads Manager | Missing or mismatched event_id, or different event names |
Use one ID from the order; match Purchase exactly |
| Duplicate purchases in GA4 | Both gtag and GTM installed, or browser and server both send | One tag per page; one purchase source of truth |
| GA4 purchases attributed to esewa.com.np | Wallet return starts a new session | Add wallet domains to unwanted referrals |
| Server events rejected for old timestamps | Website event_time older than seven days |
Send events as they happen; use the right action_source for offline |
| Low Event Match Quality | Only IP and user agent sent; phone not normalised | Add hashed email and phone (977…), external_id, fbp, fbc
|
| Purchases far above delivered orders | COD orders counted at placement, returns not removed | Move Purchase to confirmation or report delivered revenue separately |
| No server events in Test Events | Wrong dataset ID, expired token or missing test_event_code
|
Regenerate the token; check the dataset ID and payload |
| Values look wrong | Currency missing or set to USD | Send currency: 'NPR' with every value |
Setup checklist
- One data layer push per action, mapped to Meta and GA4 events.
-
Shared
event_idon Pixel and server events; unique GA4transaction_idper order. -
Email and phone normalised and SHA-256 hashed;
fbpandfbcstored with each order. -
COD rule documented: when
Purchasefires and how returns are handled. - Wallet payments verified server-side; wallet domains listed as unwanted referrals.
- Consent wired to Google and Meta tags.
- Test Events, DebugView and a weekly reconciliation in place.
Once events are reliable, use conversion rate optimisation to improve the checkout they measure, and the conversion tracking mastery guide for the wider setup.
Related resources
- GA4 server-side tracking in Nepal
- Meta Ads benchmarks Nepal
- Conversion tracking in Nepal
- Server-side tracking
- Lookalike audiences
Tracking setup is part of digital marketing for e-commerce in Nepal. To have it audited or built, see hire packages.

