mirror of
https://github.com/simstudioai/sim.git
synced 2026-10-25 09:34:44 +08:00
feat(demo): fire the X conversion event when a demo is booked (#6401)
This commit is contained in:
@@ -2,6 +2,7 @@
|
||||
|
||||
import { useEffect } from 'react'
|
||||
import Cal, { getCalApi } from '@calcom/embed-react'
|
||||
import { isHosted } from '@/lib/core/config/env-flags'
|
||||
import type { DemoLead } from '@/app/(landing)/demo/components/demo-form'
|
||||
|
||||
/** The Cal.com event the demo books - set `NEXT_PUBLIC_CAL_LINK` to override. */
|
||||
@@ -14,6 +15,12 @@ const CAL_LINK = process.env.NEXT_PUBLIC_CAL_LINK ?? 'team/sim/demo'
|
||||
*/
|
||||
const CAL_BRAND_COLOR = '#6f3dfa'
|
||||
|
||||
/**
|
||||
* X (Twitter) conversion event fired when a demo is actually booked, so ad
|
||||
* delivery optimizes toward bookings rather than form submits.
|
||||
*/
|
||||
const X_DEMO_BOOKED_EVENT_ID = 'tw-q5xbl-q5xbn'
|
||||
|
||||
interface DemoSchedulerProps {
|
||||
/** The captured lead used to prefill the Cal.com booking. */
|
||||
lead: DemoLead
|
||||
@@ -21,6 +28,22 @@ interface DemoSchedulerProps {
|
||||
|
||||
let calEmbedPreloaded = false
|
||||
|
||||
/**
|
||||
* Fires the X conversion once the Cal.com booking is confirmed. There is no
|
||||
* standalone confirmation page to drop the pixel snippet into — Cal renders the
|
||||
* "you're booked" state inside its cross-origin iframe — so the embed's
|
||||
* `bookingSuccessfulV2` event is the confirmation.
|
||||
*
|
||||
* Module-scope so the same function identity can be handed to both `on` and
|
||||
* `off`. `window.twq` is only defined where {@link LandingLayout} renders the
|
||||
* pixel base code, so the optional call is a second guard for the window
|
||||
* between mount and `uwt.js` finishing — the stub `twq` queues calls made
|
||||
* before the script loads and replays them.
|
||||
*/
|
||||
function trackDemoBooked(): void {
|
||||
window.twq?.('event', X_DEMO_BOOKED_EVENT_ID, {})
|
||||
}
|
||||
|
||||
/**
|
||||
* Warm the Cal.com embed before the scheduler mounts. Loads `embed.js` and
|
||||
* issues the embed's `preload` instruction, which fetches the booker in a
|
||||
@@ -55,12 +78,27 @@ export function preloadCalEmbed(): void {
|
||||
*/
|
||||
export function DemoScheduler({ lead }: DemoSchedulerProps) {
|
||||
useEffect(() => {
|
||||
getCalApi({ namespace: CAL_NAMESPACE }).then((cal) => {
|
||||
cal('ui', {
|
||||
hideEventTypeDetails: true,
|
||||
styles: { branding: { brandColor: CAL_BRAND_COLOR } },
|
||||
let cancelled = false
|
||||
const api = getCalApi({ namespace: CAL_NAMESPACE })
|
||||
api
|
||||
.then((cal) => {
|
||||
if (cancelled) return
|
||||
cal('ui', {
|
||||
hideEventTypeDetails: true,
|
||||
styles: { branding: { brandColor: CAL_BRAND_COLOR } },
|
||||
})
|
||||
// Matches the layout's pixel gating - a self-hosted deployment loads no
|
||||
// base pixel, so it must not subscribe an ad-tracking callback either.
|
||||
if (isHosted) cal('on', { action: 'bookingSuccessfulV2', callback: trackDemoBooked })
|
||||
})
|
||||
})
|
||||
.catch(() => {})
|
||||
return () => {
|
||||
cancelled = true
|
||||
if (!isHosted) return
|
||||
api
|
||||
.then((cal) => cal('off', { action: 'bookingSuccessfulV2', callback: trackDemoBooked }))
|
||||
.catch(() => {})
|
||||
}
|
||||
}, [])
|
||||
|
||||
return (
|
||||
|
||||
Reference in New Issue
Block a user