How Smolhub's Meta Conversions API (CAPI) sends now include real browser signals for website bookings — raising Event Match Quality without ever sending fabricated data for bookings that never touched a website.
flowchart LR
subgraph L1["Real-time — every website booking visit"]
A["Visitor's browser<br/>Lands on booking thank-you page<br/>real _fbp / _fbc cookies already set"]
B["CF Worker<br/>smolsites-ops<br/>reads cookies, cf-connecting-ip, user-agent"]
C["Smolhub<br/>POST /api/meta-events/capi-signal<br/>stores keyed by client, pat, atid"]
A -->|thank-you request| B
B -->|POST capture| C
end
subgraph L2["Every ~30 minutes — CAPI cron, all clients"]
D["PracticeHub<br/>Booking created<br/>any channel: web, WhatsApp, phone"]
E["Smolhub — CAPI cron<br/>builds Schedule / FirstBookingComplete<br/>looks up capture by pat, atid, ≤ 7 days"]
D --> E
end
G["No matching capture<br/>e.g. WhatsApp / phone booking"]
G -.->|no capture, sent without those fields| E
C -->|found, attach fbc/fbp/IP/UA| E
F["Meta / Graph API<br/>receives pixel + CAPI events<br/>same event_id on both channels"]
E -->|CAPI event| F
A -.->|Meta pixel fbq: same real signals, already automatic| F
classDef browser fill:#2a78d6,color:#fff,stroke:#1c5cab
classDef worker fill:#1baf7a,color:#fff,stroke:#128a5c
classDef hub fill:#4a3aa7,color:#fff,stroke:#352878
classDef ph fill:#eb6834,color:#fff,stroke:#b94e22
classDef meta fill:#e34948,color:#fff,stroke:#a92e2d
classDef nocap fill:#898781,color:#fff,stroke:#6b6a64,stroke-dasharray: 4 3
class A browser
class B worker
class C,E hub
class D ph
class F meta
class G nocap
No fabrication rule: the only fields that ever reach Meta are ones a
real request produced. A booking with no capture row (the muted path) sends
without fbc/fbp/client_ip_address/client_user_agent —
exactly what happens today. Nothing is invented to raise the score.
Join key: patient.hashed_id + appointment_type_id — the
same pair already used to build the shared event_id that lets Meta
dedupe the pixel and CAPI deliveries for one booking.