@od-oneapp/analytics 2026.1.1301

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (184) hide show
  1. package/README.md +509 -0
  2. package/dist/ai-YMnynb-t.mjs +3347 -0
  3. package/dist/ai-YMnynb-t.mjs.map +1 -0
  4. package/dist/chunk-DQk6qfdC.mjs +18 -0
  5. package/dist/client-CTzJVFU5.mjs +9 -0
  6. package/dist/client-CTzJVFU5.mjs.map +1 -0
  7. package/dist/client-CcFTauAh.mjs +54 -0
  8. package/dist/client-CcFTauAh.mjs.map +1 -0
  9. package/dist/client-CeOLjbac.mjs +281 -0
  10. package/dist/client-CeOLjbac.mjs.map +1 -0
  11. package/dist/client-D339NFJS.mjs +267 -0
  12. package/dist/client-D339NFJS.mjs.map +1 -0
  13. package/dist/client-next.d.mts +62 -0
  14. package/dist/client-next.d.mts.map +1 -0
  15. package/dist/client-next.mjs +525 -0
  16. package/dist/client-next.mjs.map +1 -0
  17. package/dist/client.d.mts +30 -0
  18. package/dist/client.d.mts.map +1 -0
  19. package/dist/client.mjs +186 -0
  20. package/dist/client.mjs.map +1 -0
  21. package/dist/config-DPS6bSYo.d.mts +34 -0
  22. package/dist/config-DPS6bSYo.d.mts.map +1 -0
  23. package/dist/config-P6P5adJg.mjs +287 -0
  24. package/dist/config-P6P5adJg.mjs.map +1 -0
  25. package/dist/console-8bND3mMU.mjs +128 -0
  26. package/dist/console-8bND3mMU.mjs.map +1 -0
  27. package/dist/ecommerce-Cgu4wlux.mjs +993 -0
  28. package/dist/ecommerce-Cgu4wlux.mjs.map +1 -0
  29. package/dist/emitters-6-nKo8i-.mjs +208 -0
  30. package/dist/emitters-6-nKo8i-.mjs.map +1 -0
  31. package/dist/emitters-DldkVSPp.d.mts +12 -0
  32. package/dist/emitters-DldkVSPp.d.mts.map +1 -0
  33. package/dist/index-BfNWgfa5.d.mts +1494 -0
  34. package/dist/index-BfNWgfa5.d.mts.map +1 -0
  35. package/dist/index-BkIWe--N.d.mts +953 -0
  36. package/dist/index-BkIWe--N.d.mts.map +1 -0
  37. package/dist/index-jPzXRn52.d.mts +184 -0
  38. package/dist/index-jPzXRn52.d.mts.map +1 -0
  39. package/dist/manager-DvRRjza6.d.mts +76 -0
  40. package/dist/manager-DvRRjza6.d.mts.map +1 -0
  41. package/dist/posthog-bootstrap-CYfIy_WS.mjs +1769 -0
  42. package/dist/posthog-bootstrap-CYfIy_WS.mjs.map +1 -0
  43. package/dist/posthog-bootstrap-DWxFrxlt.d.mts +81 -0
  44. package/dist/posthog-bootstrap-DWxFrxlt.d.mts.map +1 -0
  45. package/dist/providers-http-client.d.mts +37 -0
  46. package/dist/providers-http-client.d.mts.map +1 -0
  47. package/dist/providers-http-client.mjs +320 -0
  48. package/dist/providers-http-client.mjs.map +1 -0
  49. package/dist/providers-http-server.d.mts +31 -0
  50. package/dist/providers-http-server.d.mts.map +1 -0
  51. package/dist/providers-http-server.mjs +297 -0
  52. package/dist/providers-http-server.mjs.map +1 -0
  53. package/dist/providers-http.d.mts +46 -0
  54. package/dist/providers-http.d.mts.map +1 -0
  55. package/dist/providers-http.mjs +4 -0
  56. package/dist/server-edge.d.mts +9 -0
  57. package/dist/server-edge.d.mts.map +1 -0
  58. package/dist/server-edge.mjs +373 -0
  59. package/dist/server-edge.mjs.map +1 -0
  60. package/dist/server-next.d.mts +67 -0
  61. package/dist/server-next.d.mts.map +1 -0
  62. package/dist/server-next.mjs +193 -0
  63. package/dist/server-next.mjs.map +1 -0
  64. package/dist/server.d.mts +10 -0
  65. package/dist/server.mjs +7 -0
  66. package/dist/service-cYtBBL8x.mjs +945 -0
  67. package/dist/service-cYtBBL8x.mjs.map +1 -0
  68. package/dist/shared.d.mts +16 -0
  69. package/dist/shared.d.mts.map +1 -0
  70. package/dist/shared.mjs +93 -0
  71. package/dist/shared.mjs.map +1 -0
  72. package/dist/types-BxBnNQ0V.d.mts +354 -0
  73. package/dist/types-BxBnNQ0V.d.mts.map +1 -0
  74. package/dist/types-CBvxUEaF.d.mts +216 -0
  75. package/dist/types-CBvxUEaF.d.mts.map +1 -0
  76. package/dist/types.d.mts +4 -0
  77. package/dist/types.mjs +0 -0
  78. package/dist/vercel-types-lwakUfoI.d.mts +102 -0
  79. package/dist/vercel-types-lwakUfoI.d.mts.map +1 -0
  80. package/package.json +129 -0
  81. package/src/client/index.ts +164 -0
  82. package/src/client/manager.ts +71 -0
  83. package/src/client/next/components.tsx +270 -0
  84. package/src/client/next/hooks.ts +217 -0
  85. package/src/client/next/manager.ts +141 -0
  86. package/src/client/next.ts +144 -0
  87. package/src/client-next.ts +101 -0
  88. package/src/client.ts +89 -0
  89. package/src/examples/ai-sdk-patterns.ts +583 -0
  90. package/src/examples/emitter-patterns.ts +476 -0
  91. package/src/examples/nextjs-emitter-patterns.tsx +403 -0
  92. package/src/next/app-router.tsx +564 -0
  93. package/src/next/client.ts +419 -0
  94. package/src/next/index.ts +84 -0
  95. package/src/next/middleware.ts +429 -0
  96. package/src/next/rsc.tsx +300 -0
  97. package/src/next/server.ts +253 -0
  98. package/src/next/types.d.ts +220 -0
  99. package/src/providers/base-provider.ts +419 -0
  100. package/src/providers/console/client.ts +10 -0
  101. package/src/providers/console/index.ts +152 -0
  102. package/src/providers/console/server.ts +6 -0
  103. package/src/providers/console/types.ts +15 -0
  104. package/src/providers/http/client.ts +464 -0
  105. package/src/providers/http/index.ts +30 -0
  106. package/src/providers/http/server.ts +396 -0
  107. package/src/providers/http/types.ts +135 -0
  108. package/src/providers/posthog/client.ts +518 -0
  109. package/src/providers/posthog/index.ts +11 -0
  110. package/src/providers/posthog/server.ts +329 -0
  111. package/src/providers/posthog/types.ts +104 -0
  112. package/src/providers/segment/client.ts +113 -0
  113. package/src/providers/segment/index.ts +11 -0
  114. package/src/providers/segment/server.ts +115 -0
  115. package/src/providers/segment/types.ts +51 -0
  116. package/src/providers/vercel/client.ts +102 -0
  117. package/src/providers/vercel/index.ts +11 -0
  118. package/src/providers/vercel/server.ts +89 -0
  119. package/src/providers/vercel/types.ts +27 -0
  120. package/src/server/index.ts +103 -0
  121. package/src/server/manager.ts +62 -0
  122. package/src/server/next.ts +210 -0
  123. package/src/server-edge.ts +442 -0
  124. package/src/server-next.ts +39 -0
  125. package/src/server.ts +106 -0
  126. package/src/shared/emitters/ai/README.md +981 -0
  127. package/src/shared/emitters/ai/events/agent.ts +130 -0
  128. package/src/shared/emitters/ai/events/artifacts.ts +167 -0
  129. package/src/shared/emitters/ai/events/chat.ts +126 -0
  130. package/src/shared/emitters/ai/events/chatbot-ecommerce.ts +133 -0
  131. package/src/shared/emitters/ai/events/completion.ts +103 -0
  132. package/src/shared/emitters/ai/events/content-generation.ts +347 -0
  133. package/src/shared/emitters/ai/events/conversation.ts +332 -0
  134. package/src/shared/emitters/ai/events/product-features.ts +1402 -0
  135. package/src/shared/emitters/ai/events/streaming.ts +114 -0
  136. package/src/shared/emitters/ai/events/tool.ts +93 -0
  137. package/src/shared/emitters/ai/index.ts +69 -0
  138. package/src/shared/emitters/ai/track-ai-sdk.ts +74 -0
  139. package/src/shared/emitters/ai/track-ai.ts +50 -0
  140. package/src/shared/emitters/ai/types.ts +1041 -0
  141. package/src/shared/emitters/ai/utils.ts +468 -0
  142. package/src/shared/emitters/ecommerce/events/cart-checkout.ts +106 -0
  143. package/src/shared/emitters/ecommerce/events/coupon.ts +49 -0
  144. package/src/shared/emitters/ecommerce/events/engagement.ts +61 -0
  145. package/src/shared/emitters/ecommerce/events/marketplace.ts +119 -0
  146. package/src/shared/emitters/ecommerce/events/order.ts +199 -0
  147. package/src/shared/emitters/ecommerce/events/product.ts +205 -0
  148. package/src/shared/emitters/ecommerce/events/registry.ts +123 -0
  149. package/src/shared/emitters/ecommerce/events/wishlist-sharing.ts +140 -0
  150. package/src/shared/emitters/ecommerce/index.ts +46 -0
  151. package/src/shared/emitters/ecommerce/track-ecommerce.ts +53 -0
  152. package/src/shared/emitters/ecommerce/types.ts +314 -0
  153. package/src/shared/emitters/ecommerce/utils.ts +216 -0
  154. package/src/shared/emitters/emitter-types.ts +974 -0
  155. package/src/shared/emitters/emitters.ts +292 -0
  156. package/src/shared/emitters/helpers.ts +419 -0
  157. package/src/shared/emitters/index.ts +66 -0
  158. package/src/shared/index.ts +142 -0
  159. package/src/shared/ingestion/index.ts +66 -0
  160. package/src/shared/ingestion/schemas.ts +386 -0
  161. package/src/shared/ingestion/service.ts +628 -0
  162. package/src/shared/node22-features.ts +848 -0
  163. package/src/shared/providers/console-provider.ts +160 -0
  164. package/src/shared/types/base-types.ts +54 -0
  165. package/src/shared/types/console-types.ts +19 -0
  166. package/src/shared/types/posthog-types.ts +131 -0
  167. package/src/shared/types/segment-types.ts +15 -0
  168. package/src/shared/types/types.ts +397 -0
  169. package/src/shared/types/vercel-types.ts +19 -0
  170. package/src/shared/utils/config-client.ts +19 -0
  171. package/src/shared/utils/config.ts +250 -0
  172. package/src/shared/utils/emitter-adapter.ts +212 -0
  173. package/src/shared/utils/manager.test.ts +36 -0
  174. package/src/shared/utils/manager.ts +1322 -0
  175. package/src/shared/utils/posthog-bootstrap.ts +136 -0
  176. package/src/shared/utils/posthog-client-utils.ts +48 -0
  177. package/src/shared/utils/posthog-next-utils.ts +282 -0
  178. package/src/shared/utils/posthog-server-utils.ts +210 -0
  179. package/src/shared/utils/rate-limit.ts +289 -0
  180. package/src/shared/utils/security.ts +545 -0
  181. package/src/shared/utils/validation-client.ts +161 -0
  182. package/src/shared/utils/validation.ts +399 -0
  183. package/src/shared.ts +155 -0
  184. package/src/types/index.ts +62 -0
@@ -0,0 +1,419 @@
1
+ /**
2
+ * @fileoverview Next.js client-side analytics implementation
3
+ *
4
+ * Provides client-side analytics functionality for Next.js applications.
5
+ * Includes consent management, event buffering, and PostHog bootstrap integration.
6
+ *
7
+ * @remarks
8
+ * This implementation is optimized for Next.js client components:
9
+ * - Supports consent-based initialization
10
+ * - Buffers events before initialization
11
+ * - Integrates with Next.js Script component
12
+ * - Handles PostHog bootstrap data for SSR
13
+ *
14
+ * @module @od-oneapp/analytics/next/client
15
+ */
16
+
17
+ import { type AnalyticsManager } from '../shared/utils/manager';
18
+ import { createPostHogConfig } from '../shared/utils/posthog-client-utils';
19
+
20
+ import type { BootstrapData } from '../shared/types/posthog-types';
21
+ import type { AnalyticsConfig, TrackingOptions } from '../shared/types/types';
22
+
23
+ export interface NextJSClientAnalyticsConfig extends AnalyticsConfig {
24
+ nextjs?: {
25
+ // Next.js Script loading strategy
26
+ strategy?: 'afterInteractive' | 'beforeInteractive' | 'lazyOnload' | 'worker' | undefined;
27
+
28
+ // Defer initialization until user consent
29
+ deferUntilConsent?: boolean | undefined;
30
+
31
+ // Buffer events before initialization
32
+ bufferEvents?: boolean | undefined;
33
+
34
+ // Maximum events to buffer
35
+ maxBufferSize?: number | undefined;
36
+
37
+ // Custom consent check function
38
+ checkConsent?: (() => boolean | Promise<boolean>) | undefined;
39
+
40
+ // Enable debug mode
41
+ debug?: boolean | undefined;
42
+
43
+ // PostHog specific options
44
+ posthog?: {
45
+ // Server-side bootstrap data
46
+ bootstrap?: BootstrapData | undefined;
47
+
48
+ // API key for client operations
49
+ apiKey?: string | undefined;
50
+
51
+ // Host override
52
+ host?: string | undefined;
53
+ };
54
+ };
55
+ }
56
+
57
+ interface BufferedEvent {
58
+ args: any[];
59
+ method: 'track' | 'identify' | 'page' | 'group' | 'alias';
60
+ timestamp: number;
61
+ }
62
+
63
+ export class NextJSClientAnalyticsManager {
64
+ private manager: AnalyticsManager | null = null;
65
+ private config: NextJSClientAnalyticsConfig;
66
+ private isInitialized = false;
67
+ private isLoading = false;
68
+ private eventBuffer: BufferedEvent[] = [];
69
+ private consentGiven = false;
70
+
71
+ constructor(config: NextJSClientAnalyticsConfig) {
72
+ this.config = config;
73
+
74
+ // Check if we should buffer events
75
+ if (config.nextjs?.bufferEvents !== false) {
76
+ this.setupEventBuffering();
77
+ }
78
+
79
+ // Auto-initialize if no consent required
80
+ if (!config.nextjs?.deferUntilConsent) {
81
+ void this.initializeWhenReady();
82
+ }
83
+ }
84
+
85
+ /**
86
+ * Initialize analytics when DOM is ready
87
+ */
88
+ private async initializeWhenReady(): Promise<void> {
89
+ if (typeof window === 'undefined') return;
90
+
91
+ // Wait for DOM to be ready
92
+ if (document.readyState === 'loading') {
93
+ await new Promise(resolve => {
94
+ document.addEventListener('DOMContentLoaded', resolve, { once: true });
95
+ });
96
+ }
97
+
98
+ await this.initialize();
99
+ }
100
+
101
+ /**
102
+ * Initialize analytics with consent check
103
+ */
104
+ async initialize(): Promise<void> {
105
+ if (this.isInitialized || this.isLoading) return;
106
+ this.isLoading = true;
107
+
108
+ try {
109
+ // Check consent if required
110
+ if (this.config.nextjs?.deferUntilConsent) {
111
+ const hasConsent = await this.checkConsent();
112
+ if (!hasConsent) {
113
+ // Analytics initialization deferred - no consent
114
+ this.isLoading = false;
115
+ return;
116
+ }
117
+ }
118
+
119
+ // Import only what we need for Next.js environment
120
+ const { createAnalyticsManager } = await import('../shared/utils/manager');
121
+ const { ConsoleProvider } = await import('../shared/providers/console-provider');
122
+
123
+ const CLIENT_PROVIDERS: any = {
124
+ console: (config: any) => new ConsoleProvider(config),
125
+ };
126
+
127
+ // Only import providers that are configured
128
+ const configuredProviders = Object.keys(this.config.providers);
129
+
130
+ // Dynamically import only configured providers to avoid webpack bundling unused ones
131
+ for (const providerName of configuredProviders) {
132
+ if (providerName === 'console') continue; // Already loaded above
133
+
134
+ switch (providerName) {
135
+ case 'posthog': {
136
+ const { PostHogClientProvider } = await import('../providers/posthog/client');
137
+ CLIENT_PROVIDERS.posthog = (config: any) => new PostHogClientProvider(config);
138
+ break;
139
+ }
140
+ case 'segment': {
141
+ const { SegmentClientProvider } = await import('../providers/segment/client');
142
+ CLIENT_PROVIDERS.segment = (config: any) => new SegmentClientProvider(config);
143
+ break;
144
+ }
145
+ case 'vercel': {
146
+ const { VercelClientProvider } = await import('../providers/vercel/client');
147
+ CLIENT_PROVIDERS.vercel = (config: any) => new VercelClientProvider(config);
148
+ break;
149
+ }
150
+ default:
151
+ // Skip unknown providers
152
+ break;
153
+ }
154
+ }
155
+
156
+ this.manager = createAnalyticsManager(this.config, CLIENT_PROVIDERS);
157
+ await this.manager.initialize();
158
+ this.isInitialized = true;
159
+ this.consentGiven = true;
160
+
161
+ // Flush buffered events
162
+ await this.flushBufferedEvents();
163
+
164
+ // Analytics initialized successfully
165
+ } catch {
166
+ // Failed to initialize analytics
167
+ } finally {
168
+ this.isLoading = false;
169
+ }
170
+ }
171
+
172
+ /**
173
+ * Grant consent and initialize analytics
174
+ */
175
+ async grantConsent(): Promise<void> {
176
+ this.consentGiven = true;
177
+ await this.initialize();
178
+ }
179
+
180
+ /**
181
+ * Revoke consent and clear data
182
+ */
183
+ revokeConsent(): void {
184
+ this.consentGiven = false;
185
+ this.isInitialized = false;
186
+ this.manager = null;
187
+ this.eventBuffer = [];
188
+
189
+ // Analytics consent revoked
190
+ }
191
+
192
+ /**
193
+ * Check consent status
194
+ */
195
+ private async checkConsent(): Promise<boolean> {
196
+ if (this.consentGiven) return true;
197
+
198
+ if (this.config.nextjs?.checkConsent) {
199
+ return await this.config.nextjs.checkConsent();
200
+ }
201
+
202
+ return !this.config.nextjs?.deferUntilConsent;
203
+ }
204
+
205
+ /**
206
+ * Setup event buffering
207
+ */
208
+ private setupEventBuffering(): void {
209
+ const maxSize = this.config.nextjs?.maxBufferSize ?? 50;
210
+
211
+ // Ensure buffer doesn't grow too large
212
+ const intervalId = setInterval(() => {
213
+ if (this.eventBuffer.length > maxSize) {
214
+ this.eventBuffer = this.eventBuffer.slice(-maxSize);
215
+ // Analytics buffer trimmed
216
+ }
217
+ }, 5000);
218
+ // Store interval ID for potential cleanup (not used currently)
219
+ void intervalId;
220
+ }
221
+
222
+ /**
223
+ * Buffer an event if not initialized
224
+ */
225
+ private bufferEvent(method: BufferedEvent['method'], args: any[]): void {
226
+ if (!this.config.nextjs?.bufferEvents) return;
227
+
228
+ this.eventBuffer.push({
229
+ args,
230
+ method,
231
+ timestamp: Date.now(),
232
+ });
233
+
234
+ // Event buffered
235
+ }
236
+
237
+ /**
238
+ * Flush all buffered events
239
+ */
240
+ private async flushBufferedEvents(): Promise<void> {
241
+ if (!this.manager || this.eventBuffer.length === 0) return;
242
+
243
+ // Flushing buffered events
244
+
245
+ const events = [...this.eventBuffer];
246
+ this.eventBuffer = [];
247
+
248
+ for (const event of events) {
249
+ try {
250
+ switch (event.method) {
251
+ case 'track':
252
+ await this.manager.track(event.args[0], event.args[1], event.args[2]);
253
+ break;
254
+ case 'identify':
255
+ await this.manager.identify(event.args[0], event.args[1], event.args[2]);
256
+ break;
257
+ case 'page':
258
+ await this.manager.page(event.args[0], event.args[1], event.args[2]);
259
+ break;
260
+ case 'group':
261
+ await this.manager.group(event.args[0], event.args[1], event.args[2]);
262
+ break;
263
+ case 'alias':
264
+ await this.manager.alias(event.args[0], event.args[1], event.args[2]);
265
+ break;
266
+ }
267
+ } catch {
268
+ // Error flushing buffered event
269
+ }
270
+ }
271
+ }
272
+
273
+ /**
274
+ * Track an event (with buffering support)
275
+ */
276
+ async track(event: string, properties?: any, options?: TrackingOptions): Promise<void> {
277
+ if (this.isInitialized && this.manager) {
278
+ await this.manager.track(event, properties, options);
279
+ } else if (this.config.nextjs?.bufferEvents !== false) {
280
+ this.bufferEvent('track', [event, properties, options]);
281
+ }
282
+ }
283
+
284
+ /**
285
+ * Identify a user (with buffering support)
286
+ */
287
+ async identify(userId: string, traits?: any, options?: TrackingOptions): Promise<void> {
288
+ if (this.isInitialized && this.manager) {
289
+ await this.manager.identify(userId, traits, options);
290
+ } else if (this.config.nextjs?.bufferEvents !== false) {
291
+ this.bufferEvent('identify', [userId, traits, options]);
292
+ }
293
+ }
294
+
295
+ /**
296
+ * Track a page view (with buffering support)
297
+ */
298
+ async page(name?: string, properties?: any, options?: TrackingOptions): Promise<void> {
299
+ if (this.isInitialized && this.manager) {
300
+ await this.manager.page(name, properties, options);
301
+ } else if (this.config.nextjs?.bufferEvents !== false) {
302
+ this.bufferEvent('page', [name, properties, options]);
303
+ }
304
+ }
305
+
306
+ /**
307
+ * Track a group (with buffering support)
308
+ */
309
+ async group(groupId: string, traits?: any, options?: TrackingOptions): Promise<void> {
310
+ if (this.isInitialized && this.manager) {
311
+ await this.manager.group(groupId, traits, options);
312
+ } else if (this.config.nextjs?.bufferEvents !== false) {
313
+ this.bufferEvent('group', [groupId, traits, options]);
314
+ }
315
+ }
316
+
317
+ /**
318
+ * Alias a user (with buffering support)
319
+ */
320
+ async alias(userId: string, previousId: string, options?: TrackingOptions): Promise<void> {
321
+ if (this.isInitialized && this.manager) {
322
+ await this.manager.alias(userId, previousId, options);
323
+ } else if (this.config.nextjs?.bufferEvents !== false) {
324
+ this.bufferEvent('alias', [userId, previousId, options]);
325
+ }
326
+ }
327
+
328
+ /**
329
+ * Get initialization status
330
+ */
331
+ getStatus() {
332
+ return {
333
+ activeProviders: this.manager?.getActiveProviders() ?? [],
334
+ bufferedEvents: this.eventBuffer.length,
335
+ consentGiven: this.consentGiven,
336
+ isInitialized: this.isInitialized,
337
+ isLoading: this.isLoading,
338
+ };
339
+ }
340
+ }
341
+
342
+ /**
343
+ * Create a Next.js optimized analytics instance for client
344
+ *
345
+ * @example
346
+ * ```typescript
347
+ * const analytics = createNextJSClientAnalytics({
348
+ * providers: { posthog: { apiKey: 'phc_xxx' } },
349
+ * nextjs: { deferUntilConsent: true },
350
+ * });
351
+ * await analytics.initialize();
352
+ * ```
353
+ */
354
+ export function createNextJSClientAnalytics(
355
+ config: NextJSClientAnalyticsConfig,
356
+ ): NextJSClientAnalyticsManager {
357
+ return new NextJSClientAnalyticsManager(config);
358
+ }
359
+
360
+ /**
361
+ * Next.js Script component integration helper
362
+ *
363
+ * @example
364
+ * ```tsx
365
+ * <Script {...getAnalyticsScriptProps('afterInteractive')} src="/analytics.js" />
366
+ * ```
367
+ */
368
+ export function getAnalyticsScriptProps(
369
+ strategy: 'afterInteractive' | 'beforeInteractive' | 'lazyOnload' = 'afterInteractive',
370
+ ) {
371
+ return {
372
+ onLoad: () => {
373
+ if (typeof window !== 'undefined') {
374
+ // Analytics scripts have loaded, can now initialize
375
+ window.dispatchEvent(new CustomEvent('analytics:scripts-loaded'));
376
+ }
377
+ },
378
+ strategy,
379
+ };
380
+ }
381
+
382
+ /**
383
+ * Create PostHog config with bootstrap data for client
384
+ *
385
+ * @example
386
+ * ```typescript
387
+ * const config = createPostHogConfigWithBootstrap(apiKey, bootstrapData);
388
+ * const analytics = createNextJSClientAnalytics(config);
389
+ * ```
390
+ */
391
+ export function createPostHogConfigWithBootstrap(
392
+ apiKey: string,
393
+ bootstrapData: BootstrapData,
394
+ options?: {
395
+ host?: string;
396
+ autocapture?: boolean;
397
+ capture_pageview?: boolean;
398
+ session_recording?: boolean;
399
+ debug?: boolean;
400
+ },
401
+ ): NextJSClientAnalyticsConfig {
402
+ const posthogConfig = createPostHogConfig(apiKey, {
403
+ ...options,
404
+ bootstrap: bootstrapData,
405
+ });
406
+
407
+ return {
408
+ providers: {
409
+ posthog: posthogConfig,
410
+ },
411
+ nextjs: {
412
+ posthog: {
413
+ apiKey,
414
+ bootstrap: bootstrapData,
415
+ ...(options?.host !== undefined && { host: options.host }),
416
+ },
417
+ },
418
+ };
419
+ }
@@ -0,0 +1,84 @@
1
+ /**
2
+ * @fileoverview Next.js Analytics Integration
3
+ *
4
+ * Comprehensive analytics solution for Next.js 15 with App Router support.
5
+ * Provides client-side, server-side, React Server Component, middleware, and
6
+ * App Router integrations for analytics tracking.
7
+ *
8
+ * @module @od-oneapp/analytics/next
9
+ */
10
+
11
+ // Client-side exports
12
+ export {
13
+ NextJSClientAnalyticsManager,
14
+ createNextJSClientAnalytics,
15
+ createPostHogConfigWithBootstrap,
16
+ getAnalyticsScriptProps,
17
+ type NextJSClientAnalyticsConfig,
18
+ } from './client';
19
+
20
+ // Server-side exports
21
+ export {
22
+ NextJSServerAnalyticsManager,
23
+ createNextJSServerAnalytics,
24
+ createNextJSServerAnalyticsWithBootstrap,
25
+ getPostHogBootstrapDataOnServer,
26
+ type NextJSServerAnalyticsConfig,
27
+ } from './server';
28
+
29
+ // React Server Component exports
30
+ export {
31
+ ServerAnalyticsProvider,
32
+ getServerBootstrapData,
33
+ identifyServerUser,
34
+ identifyUserAction,
35
+ trackEventAction,
36
+ trackServerEvent,
37
+ trackServerPageView,
38
+ withServerPageTracking,
39
+ } from './rsc';
40
+
41
+ // App Router specific exports
42
+ export {
43
+ AnalyticsProvider as ClientAnalyticsProvider,
44
+ TrackedButton,
45
+ TrackedLink,
46
+ resetAnalytics,
47
+ useAnalytics,
48
+ useAnalyticsConsent,
49
+ useEcommerceTracking,
50
+ useFormTracking,
51
+ useIdentifyUser,
52
+ usePageTracking,
53
+ useTrackEvent,
54
+ withViewTracking,
55
+ } from './app-router';
56
+
57
+ // Middleware exports
58
+ export {
59
+ composeMiddleware,
60
+ conditionalAnalyticsMiddleware,
61
+ createAnalyticsMiddleware,
62
+ createAnalyticsMiddlewareConfig,
63
+ getAnalyticsContextFromHeaders,
64
+ getDistinctIdFromHeaders,
65
+ type AnalyticsMiddlewareConfig,
66
+ } from './middleware';
67
+
68
+ // Re-export types
69
+ export type {
70
+ AnalyticsConfig,
71
+ AnalyticsContext,
72
+ AnalyticsProvider,
73
+ ProviderConfig,
74
+ TrackingOptions,
75
+ } from '../shared/types/types';
76
+
77
+ export type { BootstrapData, PostHogConfig } from '../shared/types/posthog-types';
78
+
79
+ // Export utilities
80
+ export {
81
+ createBootstrapData,
82
+ generateDistinctId,
83
+ getDistinctIdFromCookies,
84
+ } from '../shared/utils/posthog-bootstrap';