TRACKING SPECIALIST — BARIS ASA · LONDON
Synctag
Start the check → TRACKING SPECIALIST — BARIS ASA · LONDON
F-301
F-301 · ECOMMERCE & RECONCILIATION · FILED 2026 · REVISED 15 JUN 2026 · FREQ ▮▮▮▮▯

Ecommerce events partial

Also filed as “ga4 funnel missing steps”“add_to_cart not showing in ga4”“ga4 ecommerce report empty mid funnel”“ga4 only tracking purchases not the rest”“ga4 doesn't match shopify totals”“begin_checkout event missing in ga4”

Ecommerce events partial is an incomplete GA4 ecommerce implementation: only some of the prescribed events fire, or their items array lacks detail. Purchase usually lands, but mid-funnel rungs like view_item, add_to_cart and begin_checkout never send, so GA4 cannot show where shoppers drop off and its totals will not reconcile with the store.

Symptom and cause

Symptom
Funnel blind spots: you can see purchases but not where shoppers drop off. GA4 never reconciles with the store platform.
Cause
Only some of the ecommerce events are implemented (purchase but not add_to_cart / begin_checkout), or the data layer is missing item-level detail.
Where it's caught
GA4 ecommerce reports with gaps mid-funnel; item or revenue totals that don't match Shopify/Woo/the backend.

Where the funnel goes dark

GA4 builds its ecommerce reports from a prescribed event set fired in funnel order: view_item_list, select_item, view_item, add_to_cart, view_cart, begin_checkout, add_shipping_info, add_payment_info, purchase, plus refund. Each event is a discrete measurement point, so an event that is never sent produces no rows, and any report step or funnel rung keyed on it is simply empty. GA4 does not fail loudly here. It silently mislocates the drop-off: the funnel appears to begin at the first instrumented step, the missing upstream rungs read zero, and the genuine upper-funnel abandonment is invisible. Two further constraints decide whether the data is usable. First, the names are load-bearing for reporting, not for validation: the prebuilt Monetisation, ecommerce and Checkout journey reports populate only from the prescribed recommended names and their required parameters. Fire the same logical step under a non-standard name (AddToCart, cart_add) and GA4 still accepts the hit, but records it as a generic custom event that never feeds those reports. These names are not reserved in the strict GA4 sense (the reserved list is automatically collected names and reserved prefixes), so the constraint is which reports get fed, not whether the event is rejected. Second, every event carries an items array, and within each item at least one of item_id or item_name is required for the item-scoped dimensions and the item revenue and quantity metrics to populate. An event can fire with an empty or mistyped items array and still be accepted, leaving those columns blank. The register names both halves: missing events and missing item-level detail. The Checkout journey report is the native readout, its four rungs powered exactly by begin_checkout, add_shipping_info, add_payment_info and purchase, and a rung shows no data when its event is not implemented. Its companion is the Purchase journey report (Reports > Life cycle > Monetization > Purchase journey), whose closed funnel runs session_start, view_item, add_to_cart, begin_checkout and purchase. Because it is closed by default, a missing upstream rung drops every user out and blanks every step below it, so to localise WHICH upper rung is absent you switch the report (or an Explore Funnel exploration) to open-funnel mode; closed, the prebuilt report only confirms the funnel breaks, not where.

GA4 · ecommerce events by step · open Funnel exploration · reconstructed
view_item never sent · should be here
add_to_cart never sent · should be here
begin_checkout never sent · should be here
add_payment_info first instrumented rung, so the funnel looks like it starts here
purchase fires, and roughly reconciles to orders
Funnel stepEvents in GA4In store data
view_item— not sentpresent
add_to_cart— not sentpresent
begin_checkout— not sentpresent
add_payment_infoyespresent
purchaseyespresent

How to catch it

  1. Walk the journey live in DebugView (Admin > Data display > DebugView, with debug mode on, most simply by browsing the site in GTM Preview / Tag Assistant or with the GA Debugger extension active, so the events carry the debug flag). DebugView's DEBUG DEVICE selector only shows devices that have recently been streaming events, so a device drops off the list once it goes quiet (around the same 30-minute horizon as the DebugView event stream); confirm your own session is the one selected in the Device selector before concluding an event is missing, and re-trigger the journey if your device has dropped off the list. Move from a product page through the cart to a test purchase and watch which event names stream in. The fault shows as a gap: view_item or add_to_cart or begin_checkout never appears while purchase does. Paths and menus here are current as of mid-2026.
  2. Open a streamed event in DebugView and look at its Items tab (the separate items card GA4 adds to any event that carried an items array). A wholly absent items key shows no Items tab, and in practice an empty array (items: []) shows none either. An array that does carry an item object but strips the recognised item parameters (item_id and item_name missing) can show an Items tab that is present but empty, so do not stop at the tab existing. Open it and confirm at least one item object is listed, carrying item_id or item_name with price and quantity. Both an absent Items tab and a present-but-empty one are the F-301 item-level tell, separate from the missing-event half.
  3. GA4 puts these reports under Life cycle > Monetization if the property uses the Life-cycle collection; newer properties default to Business objectives, where the same reports sit under the Drive online sales topic. Read the Checkout journey report (Reports > Life cycle > Monetization > Checkout journey, the collection appears as Life cycle and the topic as Monetization/Monetisation in the left nav, with the report itself labelled Checkout journey; or via the Drive online sales topic if the property uses the Business-objectives collection). Its four rungs are begin_checkout, add_shipping_info, add_payment_info and purchase. A rung with no data is its event not implemented, not a real shopper behaviour. The Checkout journey funnel is closed on begin_checkout: if begin_checkout itself is missing, no users enter and the whole report reads blank. Localise the absent upper rung with an open funnel: open the prebuilt Purchase journey report (Reports > Life cycle > Monetization > Purchase journey) and flip the toggle above the funnel to an open funnel. Closed, it blanks every step below the first missing rung; open, each rung reports independently and the absent one stands out. Read view_item, add_to_cart and begin_checkout there. For rungs no prebuilt report includes (view_item_list, select_item, view_cart), build an open Funnel exploration (Explore > Funnel exploration; switch on the Make open funnel toggle in Visualization settings).
  4. Prove a missing rung is a dataLayer gap, not a tag failure, in GTM Preview (launch it via tagassistant.google.com) or Tag Assistant. If there is no dataLayer push for that step at all, the event was never built (F-301). If you select the event in the Tag Assistant timeline, open the Variables tab (or the tag's resolved values) and find the ecommerce/items variable reads undefined on the first fire but populated on retest, the cause is a dataLayer race and you are looking at F-103. If the push is present and complete but the tag never fires, you have left F-301 territory entirely: this is a trigger or consent fault, not an ecommerce-completeness one. Open the tag in Tag Assistant and read its firing triggers.
  5. Separate completeness from value before concluding. If add_to_cart and begin_checkout are simply absent from the stream, it is F-301. If every event is present and only the per-order revenue or item totals diverge by a fixed amount, that is F-302, not this fault.
  6. Reconcile against the store platform honestly. Set a window of GA4 event counts and item totals against Shopify, Woo or the order table. Expect a single- to low-double-digit divergence (commonly around 10 to 20 percent) even with a clean setup (consent denial, ad blockers, client-side loss). The F-301 signal is a structurally blank funnel step or a persistent, large gap, not the mere existence of a difference.

What putting it right involves

  1. Implement the full prescribed event set in funnel order: view_item_list, select_item, view_item, add_to_cart, view_cart, begin_checkout, add_shipping_info, add_payment_info, purchase, plus refund. Use the exact recommended names, because a non-standard name is recorded as a generic custom event and will not feed the Monetisation, ecommerce or Checkout journey reports.
  2. Build a complete data layer alongside the events. Each ecommerce event gets its own discrete dataLayer push with a populated items array, at least one of item_id or item_name on every item, price and quantity supplied; GA4 types quantity as a number, but pass it as a whole number, since a floating-point quantity mis-reports item revenue in the Monetisation reports. Without item-level detail the events fire but item-scoped dimensions and item revenue stay blank.
  3. Clear the ecommerce object between events with dataLayer.push({ ecommerce: null }) before each new push, so items from one step do not bleed into the next. This is a common cause of an items array that looks present but carries products carried over from the previous step.
  4. On Shopify, treat the native Google channel as a partial subset, not the whole set. Its defaults commonly cover most of the funnel (view_item_list, view_item, add_to_cart, begin_checkout, add_shipping_info, add_payment_info, purchase), while view_cart, remove_from_cart and refund are the ones that typically need custom work via data layer and GTM or an app (refund in particular is never fired natively, so unrefunded revenue overstates). select_item is reported as native by some setups and not others, so treat it as version-dependent. The exact list is version- and setup-dependent (Web Pixels and Customer Events, store tier, Plus checkout extensibility, third-party apps), so confirm it for the specific store rather than assuming a universal list.
  5. Reconcile GA4 against the platform row by row once the events fire, and set the scope honestly. This is forward-only because the missing events were never collected, so no report can reconstruct them; the BigQuery raw export does not backfill, and explorations are additionally bounded by the data-retention window (standard aggregated reports retain longer but still have nothing to show before go-live). Frame it as starting collection from go-live, not recovering the gap.
  6. Re-verify in DebugView and the Checkout journey report after go-live, and do not treat events firing as proof of completeness. An event can fire under a wrong name, with an empty or mistyped items array, or inconsistently across browsers, and each of those still counts as partial. Confirm every rung populates with item detail attached before signing it off.
How I'd fix this

Sources on file

Questions on this file

How do I tell F-301 (events partial) apart from F-302 (value inconsistent)?

Look at whether the events exist at all. F-301 is a completeness fault: mid-funnel rungs like add_to_cart and begin_checkout are simply absent, the funnel has blank steps, and item totals are missing because the events or the items array were never built. F-302 is a consistency fault: every event fires, the funnel is complete, but the per-order revenue diverges by exactly the tax, shipping, currency or discount amount across platforms. Absent rungs is F-301. Present rungs with a fixed value gap is F-302.

Why can I see purchases in GA4 but not where shoppers drop off?

Because each step in the funnel is its own event, and a report rung shows data only if its event was sent. If purchase is the only ecommerce event implemented, GA4 has no rows for view_item, add_to_cart or begin_checkout, so the funnel appears to begin at the first instrumented step and the genuine upstream abandonment is invisible. The drop-off is not real behaviour, it is the shape of the absent events. Confirm in DebugView which event names actually stream.

GA4 doesn't reconcile with Shopify. Does that alone mean F-301?

Not on its own. GA4 ecommerce events are client-side and lossy, so a divergence of roughly 10 to 20 percent from the store is expected even with a perfect implementation, from consent denial, ad blockers and tagging gaps. F-301's signal is a structurally blank funnel step or a persistent, large gap, not any difference at all. A revenue gap that runs GA4 ahead of the store and scales with order volume (commonly 2x or more, sometimes higher) points instead at purchase double-firing (F-101); F-301 never runs GA4 ABOVE the store, missing events and item detail can only under-report, never inflate, and its defining tell is structurally blank mid-funnel rungs, which can be present even when purchase revenue itself reconciles to the store. Read the funnel for missing rungs before blaming reconciliation.

I see the events firing in DebugView. Is the implementation complete?

Not necessarily. Events firing is not proof of completeness. An event can fire under a non-standard name, in which case GA4 records it as a generic custom event that never feeds the Monetisation or Checkout journey reports. It can fire with an empty or mistyped items array, leaving item revenue and item-scoped dimensions blank. Or it can fire inconsistently across browsers and devices. Check that every rung uses the exact recommended name and carries a populated items array.

Are the GA4 ecommerce event names reserved?

No, not in the strict GA4 sense. The reserved and blocked list is automatically collected names like page_view and session_start, plus reserved prefixes. add_to_cart, view_item, begin_checkout and purchase are not on it. GA4 will accept the same step under a custom name like AddToCart. The constraint is reporting, not validation: a non-standard name is filed as a generic custom event and will not populate the prebuilt ecommerce reports. Use the prescribed names so the reports get fed.

Once I add the missing events, will GA4 fill in the historical gap?

No. The fix is forward-only. Implementing the missing events starts collection from go-live, but no report can reconstruct events that were never collected: the BigQuery export does not backfill, and explorations are additionally bounded by the data-retention window (standard aggregated reports retain longer but still have nothing to show before go-live), so the previously-missing rungs read zero for every historical date. The funnel will show a clean break at the go-live boundary, blank before, populated after. Treat it as new collection starting now, not a recovery of the period you could not see.