import { E as EventBus } from '../event-bus-Cuy2o5Z5.js'; import { P as PixelRuntimeConfig, a as PixelConfigMap } from '../types-B9JX7zpq.js'; export { C as CircuitBreakerConfig, b as CircuitBreakerState, D as DEFAULT_CIRCUIT_BREAKER_CONFIG, c as PixelRegistration, d as PixelRuntimeGlobal, R as RegisteredSDK, S as SDKAnalyticsAPI, e as SDKEvent, f as SDKEventMetadata } from '../types-B9JX7zpq.js'; import '../payloads-BYtydfZU.js'; /** * Pixel Runtime V2 — Self-Registration Model * * The platform-agnostic runtime that all pixel SDKs register with. * The runtime does NOT know about Meta, GA4, or any specific platform. * * Boot sequence: * 1. activate(pixelConfig) — subscribe to EventBus, expose window global, drain pending * 2. SDK scripts load async, call window.__OPEN_STORE_PIXEL_RUNTIME__.register() * 3. Runtime validates config, calls register(analytics, config), replays queue * 4. After 10s, window global cleaned up, queue flushed * * Key design decisions: * - Runtime owns ALL SDK subscriptions (not EventBus). Enables per-SDK replay. * - Events transformed from internal OpenStoreEvent shape to SDK-facing SDKEvent. * - Per-SDK circuit breaker (5 errors → 60s cooldown). * - Pending queue pattern handles SDK-loads-before-runtime edge case. */ type PixelRuntimeStatus = "idle" | "active" | "destroyed"; declare class PixelRuntime { private readonly bus; private readonly maxQueueSize; private readonly registrationWindowMs; private readonly consentCheck?; private readonly sdks; private eventQueue; private queueingActive; private pixelConfig; private _status; private busSubscription; private registrationTimer; constructor(bus: EventBus, config?: PixelRuntimeConfig); get status(): PixelRuntimeStatus; get sdkCount(): number; hasSDK(name: string): boolean; /** * Activate the runtime. Called once from EventProvider's useEffect. * * 1. Subscribes to ALL EventBus events (queues + forwards to registered SDKs) * 2. Exposes window.__OPEN_STORE_PIXEL_RUNTIME__ for SDK self-registration * 3. Drains any pending registrations (SDKs that loaded before us) * 4. Starts the registration window cleanup timer */ activate(pixelConfig: PixelConfigMap): void; /** * Called by each SDK script when it loads. * * FLOW: * 1. Validate config exists for this SDK (env var was set) * 2. Build analytics API (subscribe-only, no emit) * 3. Call SDK's register() — SDK calls analytics.subscribe() inside * 4. IMMEDIATELY replay all queued events to THIS SDK's callbacks * * JavaScript is single-threaded. This entire sequence is ONE synchronous call. * No EventBus emission can interrupt. Zero gap between subscribe and replay. */ private registerPixel; /** * Builds a frozen analytics object for one SDK. * * CRITICAL: subscribe() stores callbacks in the runtime's own map. * It does NOT register on EventBus. This enables per-SDK replay. */ private buildAnalyticsAPI; /** * Forwards a real-time event to ALL registered SDKs. * Called on every EventBus emission after activate(). */ private forwardToAllSDKs; /** * Delivers one event to one SDK's matching callbacks. * Handles: consent gate, circuit breaker, frozen copy, error isolation. */ private deliverEventToSDK; /** * Produces an independent deep copy of an event for a single subscriber. * * Each subscriber MUST receive its own mutable copy. Third-party pixel SDKs * mutate the payload they're handed in place (e.g. Meta's ProtectedDataMode * does `delete i[e]`), and fbq serialises props at queue-drain time — long * after the callback returns. A shared object lets one consumer corrupt * another's payload; a frozen object makes the in-place delete throw. So we * clone deeply (nested contents/content_ids independent) and never freeze. * structuredClone preserves undefined/NaN/Date; guarded so a non-cloneable * payload degrades to a shallow copy rather than breaking dispatch. */ private cloneForSubscriber; /** * Executes a single SDK callback with try/catch error isolation. * Manages per-SDK circuit breaker state. */ private executeCallback; /** * Replays ALL queued events to ONE specific SDK. * Called immediately after that SDK's register() completes. */ private replayQueueToSDK; /** * Transforms an internal OpenStoreEvent envelope into the SDK-facing SDKEvent shape. * * Internal: { event_type, data, event_id, session_id, page, cookies, user_data, ... } * SDK: { event_type, properties, metadata: { event_id, session_id, page, cookies, ... } } * * This keeps EventBus + middleware unchanged while giving SDKs the V2 event shape. */ private transformEventForSDK; /** * Deep copies an event for the queue. * Stores true deep copies so later mutations don't affect queued versions. */ private deepCopyEvent; private openCircuitBreaker; /** * Closes the registration window after the timeout period. * Removes window global and flushes the event queue. */ private closeRegistrationWindow; /** * Destroy the runtime. Called on EventProvider unmount. */ destroy(): void; } export { PixelConfigMap, PixelRuntime, PixelRuntimeConfig, type PixelRuntimeStatus };