Marketing agencies · Offline conversions

CRM conversions back to Meta and Google

Qualified leads, meetings and sales from each client's CRM sent to Meta and Google exactly once, inside the window each platform accepts.

UsageCommon
EffortMedium
ForAgencies running media for clients whose sale happens in the CRM, on WhatsApp or in store.
Source

CRM stages and sales, page tracking data

Rule

Window per destination, identifiers and event_id

Outcome

Events and audiences ready to send

Activation

Meta Conversions API and Google Ads

What it solves

  • Platforms start optimizing for qualified leads, meetings or sales, not for filled forms.
  • Each event arrives once, within the deadline the platform accepts.
  • Disqualified leads and current customers leave prospecting through exclusion audiences.

Business questions it answers

Ask your agent these questions once the case is live.

Which events were sent to Meta yesterday, by client?
How many CRM sales were sent back to Google this month?
Did match quality drop? Which fields are missing?
Does any client have the table ready and the send turned off?
How many disqualified leads are in the exclusion audience?

What you need

  • Each client's CRM connected to Nekt, with the date of each stage
  • The stages that become events and each one's value, agreed with the client
  • Meta Conversions and Google Ads destinations set up per account, with the conversion action created on the platform

What you get

  • One table per destination and per client with the current window's events
  • Normalized identifiers: email, phone, fbc and external ID
  • Customer and disqualified audiences kept up to date
  • A monitor that compares the table produced with the send made

Where to activate

Meta Conversions API

Qualification, meeting and sale events, several times a day when volume calls for it.

Google Ads Click Conversions

Won sales with a valid email, once a day.

Audiences

Customers and disqualified leads as lookalike and exclusion audiences.

Ready to build?

One pipeline per client and per destination. The logic repeats; the care is in the window, deduplication and checking that the send was counted. The detailed view has the business rules, the pitfalls and the acceptance test. Or send everything straight to your agent with the Nekt MCP.

The problem

The same sale must reach Meta and Google in different formats and deadlines. Meta rejects events older than 7 days or dated in the future; Google accepts up to 90 days from the click but rejects empty identifiers. The destination resends the whole table at every run, so whoever does not control the window sends the same event several times. And a successful run in Nekt does not prove the platform matched the sale to a click.

How it is usually done, and the rule

Each row is a mistake that already happened in practice.

The common wayThe rule
01
One conversions table for every destination.
One table per destination

Meta and Google require different columns, windows and identifiers for the same sale. Build one transformation per client and per destination, already in the destination's format. Never a single table serving both.

02
An exact 7-day window or a months-long backfill to Meta.
Window inside the limit, with margin

The Meta Conversions API rejects event_time older than 7 days: use a 6-day or 132-hour window, never exactly 7. Google Ads Click Conversions accepts up to 90 days after the click (63 days for enhanced conversions for leads): real pipelines use 55 days to leave a margin. An event dated in the future makes Meta reject the batch: cap event_time at the run time.

03
A cumulative table with the whole history.
The table holds only the current window

The destination resends the whole table at every run. So the table carries only the current window's events, tied to the run time, with disjoint windows when it runs several times a day. Each update goes out once and the daily count matches Events Manager.

04
A random event_id or one with the run date.
Deterministic event_id

Build event_id from the lead or deal ID and the event name (<id>-<event>). If the same deal comes back in a later window, it goes out with the same event_id and Meta's deduplication absorbs it. On Google, use order_id on the same principle.

05
Sending the phone number as typed.
Normalized identifiers

Email lowercase, no spaces and with an @. Phone digits only, with 55 in front when it has 10 or 11 digits, valid with 12 or 13. First name letters only. fbc in the format fb.1.<timestamp in ms>.<fbclid> when the landing URL has an fbclid; fbp, IP and user agent from the page when they exist. A row with no email and no phone does not go out.

06
Sending every new deal as Purchase.
A stage becomes an event with an agreed name and value

Each client defines which stages become events (qualified lead, meeting booked, proposal, sale) and each one's value. A sale carries the won deal value; an intermediate stage may carry an agreed fixed value. Events from the CRM alone go as system_generated (offline); events with page data go as website, the only kind that gets a match quality score.

07
Two sends of the same booking under different names.
One owner per event

If the pixel, an automation or another tool already sends an event (calendar booking, form lead), the CRM pipeline does not send the same fact under another name. Use a flag on the lead to avoid firing again and keep event names distinct between pipelines.

08
Sending the whole CRM base.
Only what may have come from the platform

Send the conversions that may have a click on the destination: when the client asks, only deals with a Meta source go to the Conversions API. Never send imported bases, test contacts or emails from the client's or the agency's team.

09
Concluding the platform received it because the table exists.
Sent is not counted

Check both sides: the transformation ran, the destination is active and ran after it. A recent transformation with an inactive destination is a signal never delivered. And even when the send is accepted, without a matching click in the window the sale does not become a conversion: the sign that it works is the offline conversion action showing conversions in the ad account.

10
Exporting the CRM list without cleaning it.
Audiences use the same cleanup

Customer audiences (Customer Match, Custom Audiences) and exclusion audiences (disqualified, current customers, another business line's base) use the same email and phone normalization, with no test or team contacts, deduplicated by phone. Disqualified is the disqualification stage or a loss for profile reasons, agreed with the client.

Limits of each destination

What each platform accepts and what the pipeline does to fit.

Meta Conversions APIevent_time up to 7 days6-day or 132-hour window
Meta · event in the futureBatch rejectedevent_time capped at the run time
Meta · deduplicationSame event_id within 48 hours<id>-<event>
Meta · action_source websiteGets a match quality scoreem, ph, fbc, fbp, IP, user agent
Meta · action_source system_generatedOffline, no match quality scoreCRM sale
Google Ads Click ConversionsUp to 90 days from the click55-day window
Google · empty identifierRow rejectedonly rows with a valid email
Customer Match and Custom AudiencesCustomer and exclusion audiencessame normalization

Definitions

Conversion event
one row per CRM record and stage, with event_name, event_time, event_id and identifiers, inside the destination's window
Current window
update interval of the records this run sends; it does not overlap the previous run's window
event_id
lead or deal ID plus the event name
Identification rate
events with a valid email or phone / eligible events in the window
Events delivered
table events covered by a completed destination run that came after the transformation
Counted conversions
conversions of the offline action in the ad account in the period (on Google, an UPLOAD_CLICKS action)
Exclusion audience
normalized contacts deduplicated by phone in a disqualification or customer stage, with no tests

Pitfalls that already happened

Half-built pipeline

The transformation ran every day and the table was right, but the destination had been inactive for weeks. Google kept optimizing for leads.

A monitor comparing the table produced with the send made.

Batch rejected by date

One event dated a few minutes in the future made Meta reject the whole batch.

Cap event_time at the run time.

Double count in Events Manager

The cumulative table was resent at every run and the same lead showed up several times a day.

Disjoint window tied to the run time.

Deduplication that did nothing

Complete and partial form responses had IDs from different spaces; deduplicating by response ID removed nothing and the lead went out twice.

Deduplicate by normalized phone within a 7-day window.

A sale that is an echo

The sale conversion in the ad account was data sent by the agency itself and was presented to the client as platform measurement.

Label offline conversions as sent by the agency.

Sent and never counted

Months of successful sends and no offline conversion attributed, because the emails did not match clicks within the window.

Track the offline action in the account, not the send status.

Acceptance test

The case is done when every item passes.

Agent package

Paste into Claude, ChatGPT or any client with the Nekt MCP connected.

Full Markdown
CRM conversions to the platforms
- Each client has one table per destination. Conversion tables are outputs for Meta and Google, not a source for results analysis.
- Meta Conversions API: event_time up to 7 days (6-day or 132-hour window) and never in the future. Deduplication by event_id within 48 hours.
- Google Ads Click Conversions: up to 90 days from the click (63 for enhanced conversions for leads); rows with no identifier are rejected.
- event_id = record ID + event name. The table holds only the current window.
- CRM-only events go as system_generated (offline, no match quality score). Events with page data go as website.
- A table produced is not a send made: confirm an active destination and a run after the transformation. A send accepted is not a counted conversion: check the offline action in the account.
- A sale conversion showing on the platform was sent by the agency. Do not present it as independent measurement.
Per-client exceptions:
- <client>: events <LeadQualificado>, <ReuniaoMarcada> and <Purchase>; LeadQualificado = lead still open <n> days after creation.
- <client>: only deals with a Meta source go to the Conversions API.
- <client>: fixed value of <x> for stage <stage> on Google.

Variations

Forms with partial responses

Partial and complete go out under the same event name, the partial event_id gets its own suffix and deduplication is by phone.

One pipeline per end client

Agencies with dozens of clinics or franchises generate one table and one destination per form, from a template.

Checkout sale

An approved sale on an info product platform sent per transaction, with a validated email.