@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,193 @@
1
+ import { _ as AnalyticsManager, a as ContextBuilder, c as createAnonymousSession, d as isGroupPayload, f as isIdentifyPayload, g as withUTM, h as withMetadata, i as getDistinctIdFromCookies, l as createUserSession, m as isTrackPayload, n as createMinimalBootstrapData, o as EventBatch, p as isPagePayload, r as generateDistinctId, s as PayloadBuilder, t as createBootstrapData, u as isAliasPayload, v as createAnalyticsManager } from "./posthog-bootstrap-CYfIy_WS.mjs";
2
+ import { a as screen, i as page, n as group, o as track, r as identify, t as alias } from "./emitters-6-nKo8i-.mjs";
3
+ import { t as ecommerce_exports } from "./ecommerce-Cgu4wlux.mjs";
4
+ import { a as createEmitterProcessor, i as validateConfig, n as createConfigBuilder, o as processEmitterPayload, r as getAnalyticsConfig, s as trackEcommerceEvent, t as PROVIDER_REQUIREMENTS } from "./config-P6P5adJg.mjs";
5
+ import { a as debugConfig, c as validateProvider, i as validateEventPayload, l as createServerAnalytics, n as createIngestionService, o as validateAnalyticsConfig, r as validateBatchPayload, s as validateConfigOrThrow, t as IngestionService, u as createServerAnalyticsUninitialized } from "./service-cYtBBL8x.mjs";
6
+
7
+ //#region src/next/middleware.ts
8
+ /**
9
+ * @fileoverview Analytics middleware factory - framework agnostic
10
+ *
11
+ * Provides automatic tracking and context extraction for analytics.
12
+ * Framework-agnostic implementation that can be used with Next.js or other frameworks.
13
+ *
14
+ * @remarks
15
+ * This middleware:
16
+ * - Automatically tracks page views and API routes
17
+ * - Extracts analytics context from request headers
18
+ * - Manages PostHog distinct IDs via cookies
19
+ * - Supports route exclusion patterns
20
+ * - Provides framework-agnostic interfaces
21
+ *
22
+ * @module @od-oneapp/analytics/next/middleware
23
+ */
24
+ /**
25
+ * Create analytics middleware (framework-agnostic)
26
+ * @param config - Middleware configuration
27
+ * @returns Middleware function that accepts a request and returns a response
28
+ */
29
+ function createAnalyticsMiddleware(config) {
30
+ return async function analyticsMiddleware(request) {
31
+ const { pathname, searchParams } = request.nextUrl;
32
+ const { method } = request;
33
+ if (!shouldTrackRoute(pathname, config)) return config.createResponse();
34
+ const response = config.createResponse();
35
+ try {
36
+ if (config.posthogApiKey) {
37
+ const distinctId = await ensureDistinctId(request, response, config.posthogApiKey);
38
+ response.headers.set("x-analytics-distinct-id", distinctId);
39
+ }
40
+ const context = extractAnalyticsContext(request);
41
+ response.headers.set("x-analytics-context", JSON.stringify(context));
42
+ if (globalThis.analytics && typeof globalThis.analytics.track === "function") {
43
+ const eventName = config.getEventName ? config.getEventName(pathname, method) : getDefaultEventName(pathname, method, config);
44
+ const properties = {
45
+ ...context,
46
+ ...config.getProperties ? config.getProperties(request) : {},
47
+ pathname,
48
+ method,
49
+ search_params: Object.fromEntries(searchParams.entries()),
50
+ timestamp: (/* @__PURE__ */ new Date()).toISOString()
51
+ };
52
+ (async () => {
53
+ try {
54
+ if (globalThis.analytics && typeof globalThis.analytics.track === "function") await globalThis.analytics.track(eventName, properties);
55
+ } catch {}
56
+ })();
57
+ }
58
+ } catch {
59
+ if (config.debug) {}
60
+ }
61
+ return response;
62
+ };
63
+ }
64
+ /**
65
+ * Ensure distinct ID exists for PostHog tracking
66
+ */
67
+ async function ensureDistinctId(request, response, apiKey) {
68
+ const existingId = getDistinctIdFromCookies(request.cookies, apiKey);
69
+ if (existingId) return existingId;
70
+ const newId = generateDistinctId();
71
+ const cookieName = `ph_${apiKey}_posthog`;
72
+ response.cookies.set(cookieName, JSON.stringify({ distinct_id: newId }), {
73
+ httpOnly: false,
74
+ maxAge: 365 * 24 * 60 * 60,
75
+ path: "/",
76
+ sameSite: "lax",
77
+ secure: false
78
+ });
79
+ return newId;
80
+ }
81
+ /**
82
+ * Check if route should be tracked
83
+ */
84
+ function shouldTrackRoute(pathname, config) {
85
+ if (config.shouldTrack) return config.shouldTrack(pathname);
86
+ if (config.excludeRoutes) {
87
+ for (const exclude of config.excludeRoutes) if (typeof exclude === "string") {
88
+ if (pathname.startsWith(exclude)) return false;
89
+ } else if (exclude instanceof RegExp && exclude.test(pathname)) return false;
90
+ }
91
+ for (const exclude of [
92
+ "/_next/",
93
+ "/favicon.ico",
94
+ "/robots.txt",
95
+ "/sitemap.xml",
96
+ "/.well-known/"
97
+ ]) if (pathname.startsWith(exclude)) return false;
98
+ const isApiRoute = pathname.startsWith("/api/");
99
+ if (isApiRoute && config.trackApiRoutes === false) return false;
100
+ if (!isApiRoute && config.trackPageViews === false) return false;
101
+ return true;
102
+ }
103
+ /**
104
+ * Extract analytics context from request
105
+ */
106
+ function extractAnalyticsContext(request) {
107
+ const { headers } = request;
108
+ return {
109
+ user_agent: headers.get("user-agent") ?? void 0,
110
+ referer: headers.get("referer") ?? void 0,
111
+ referrer: headers.get("referrer") ?? void 0,
112
+ ip: headers.get("x-forwarded-for")?.split(",")[0]?.trim() ?? headers.get("x-real-ip") ?? void 0,
113
+ city: headers.get("x-vercel-ip-city") ?? void 0,
114
+ country: headers.get("x-vercel-ip-country") ?? void 0,
115
+ region: headers.get("x-vercel-ip-country-region") ?? void 0,
116
+ host: headers.get("host") ?? void 0,
117
+ protocol: headers.get("x-forwarded-proto") ?? "https",
118
+ accept_encoding: headers.get("accept-encoding") ?? void 0,
119
+ accept_language: headers.get("accept-language") ?? void 0,
120
+ deployment_id: headers.get("x-vercel-deployment-id") ?? void 0,
121
+ edge_region: headers.get("x-vercel-edge-region") ?? void 0
122
+ };
123
+ }
124
+ /**
125
+ * Get default event name based on route type
126
+ */
127
+ function getDefaultEventName(pathname, method, _config) {
128
+ if (pathname.startsWith("/api/")) return `API ${method} Request`;
129
+ return "Page View";
130
+ }
131
+ /**
132
+ * Middleware configuration helper for common patterns (framework-agnostic)
133
+ * Note: createResponse must be provided by the framework-specific wrapper
134
+ */
135
+ function createAnalyticsMiddlewareConfig(options) {
136
+ const config = {
137
+ analytics: { providers: {} },
138
+ createResponse: options.createResponse,
139
+ ...options.debug !== void 0 && { debug: options.debug },
140
+ ...options.excludeRoutes !== void 0 && { excludeRoutes: options.excludeRoutes },
141
+ ...options.posthogApiKey !== void 0 && { posthogApiKey: options.posthogApiKey },
142
+ trackApiRoutes: true,
143
+ trackPageViews: true
144
+ };
145
+ if (options.posthogApiKey) config.analytics.providers.posthog = { apiKey: options.posthogApiKey };
146
+ if (options.segmentWriteKey) config.analytics.providers.segment = { writeKey: options.segmentWriteKey };
147
+ return config;
148
+ }
149
+ /**
150
+ * Extract analytics context from headers (framework-agnostic)
151
+ */
152
+ function getAnalyticsContextFromHeaders(headers) {
153
+ const contextHeader = headers.get("x-analytics-context");
154
+ if (!contextHeader) return {};
155
+ try {
156
+ return JSON.parse(contextHeader);
157
+ } catch {
158
+ return {};
159
+ }
160
+ }
161
+ /**
162
+ * Get distinct ID from headers (for server components)
163
+ */
164
+ function getDistinctIdFromHeaders(headers) {
165
+ return headers.get("x-analytics-distinct-id");
166
+ }
167
+ /**
168
+ * Conditional middleware helper
169
+ */
170
+ function conditionalAnalyticsMiddleware(config, condition) {
171
+ const middleware = createAnalyticsMiddleware(config);
172
+ return async function(request) {
173
+ if (condition(request)) return middleware(request);
174
+ return config.createResponse();
175
+ };
176
+ }
177
+ /**
178
+ * Compose multiple middleware functions
179
+ */
180
+ function composeMiddleware(...middlewares) {
181
+ return async function composedMiddleware(request, createResponse) {
182
+ let response = createResponse();
183
+ for (const middleware of middlewares) {
184
+ response = await middleware(request, createResponse);
185
+ if (response.status !== 200 || response.headers.get("location")) return response;
186
+ }
187
+ return response;
188
+ };
189
+ }
190
+
191
+ //#endregion
192
+ export { AnalyticsManager as AnalyticsManagerClass, ContextBuilder, EventBatch, IngestionService, PROVIDER_REQUIREMENTS, PayloadBuilder, alias, composeMiddleware, conditionalAnalyticsMiddleware, createAnalyticsManager, createAnalyticsMiddleware, createAnalyticsMiddlewareConfig, createAnonymousSession, createBootstrapData, createConfigBuilder, createEmitterProcessor, createIngestionService, createMinimalBootstrapData, createServerAnalytics, createServerAnalyticsUninitialized, createUserSession, debugConfig, ecommerce_exports as ecommerce, generateDistinctId, getAnalyticsConfig, getAnalyticsContextFromHeaders, getDistinctIdFromHeaders, group, identify, isAliasPayload, isGroupPayload, isIdentifyPayload, isPagePayload, isTrackPayload, page, processEmitterPayload, screen, track, trackEcommerceEvent, validateAnalyticsConfig, validateBatchPayload, validateConfig, validateConfigOrThrow, validateEventPayload, validateProvider, withMetadata, withUTM };
193
+ //# sourceMappingURL=server-next.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"server-next.mjs","names":[],"sources":["../src/next/middleware.ts"],"sourcesContent":["/**\n * @fileoverview Analytics middleware factory - framework agnostic\n *\n * Provides automatic tracking and context extraction for analytics.\n * Framework-agnostic implementation that can be used with Next.js or other frameworks.\n *\n * @remarks\n * This middleware:\n * - Automatically tracks page views and API routes\n * - Extracts analytics context from request headers\n * - Manages PostHog distinct IDs via cookies\n * - Supports route exclusion patterns\n * - Provides framework-agnostic interfaces\n *\n * @module @od-oneapp/analytics/next/middleware\n */\n\nimport { generateDistinctId, getDistinctIdFromCookies } from '../shared/utils/posthog-bootstrap';\n\nimport type { AnalyticsConfig } from '../shared/types/types';\n\n/**\n * Request interface for middleware (framework-agnostic)\n */\nexport interface MiddlewareRequest {\n cookies: {\n get: (name: string) => { value: string } | undefined;\n set: (name: string, value: string, options?: any) => void;\n };\n headers: Headers;\n method: string;\n nextUrl: {\n pathname: string;\n searchParams: URLSearchParams;\n };\n}\n\n/**\n * Response interface for middleware (framework-agnostic)\n */\nexport interface MiddlewareResponse {\n headers: Headers;\n status: number;\n cookies: {\n set: (name: string, value: string, options?: any) => void;\n };\n}\n\nexport interface AnalyticsMiddlewareConfig {\n /**\n * Analytics configuration\n */\n analytics: AnalyticsConfig;\n\n /**\n * PostHog API key for distinct ID management\n */\n posthogApiKey?: string;\n\n /**\n * Routes to exclude from tracking\n */\n excludeRoutes?: string[] | RegExp[];\n\n /**\n * Custom route matcher function\n */\n shouldTrack?: (pathname: string) => boolean;\n\n /**\n * Enable debug logging\n */\n debug?: boolean;\n\n /**\n * Custom event name generator\n */\n getEventName?: (pathname: string, method: string) => string;\n\n /**\n * Custom properties extractor\n */\n getProperties?: (request: MiddlewareRequest) => Record<string, any>;\n\n /**\n * Track page views automatically\n */\n trackPageViews?: boolean;\n\n /**\n * Track API routes automatically\n */\n trackApiRoutes?: boolean;\n\n /**\n * Factory function to create response (framework-specific)\n */\n createResponse: () => MiddlewareResponse;\n}\n\n/**\n * Create analytics middleware (framework-agnostic)\n * @param config - Middleware configuration\n * @returns Middleware function that accepts a request and returns a response\n */\nexport function createAnalyticsMiddleware(config: AnalyticsMiddlewareConfig) {\n return async function analyticsMiddleware(\n request: MiddlewareRequest,\n ): Promise<MiddlewareResponse> {\n const { pathname, searchParams } = request.nextUrl;\n const { method } = request;\n\n // Check if we should track this route\n if (!shouldTrackRoute(pathname, config)) {\n return config.createResponse();\n }\n\n // Create response object to modify headers/cookies\n const response = config.createResponse();\n\n try {\n // Handle distinct ID for PostHog\n if (config.posthogApiKey) {\n const distinctId = await ensureDistinctId(request, response, config.posthogApiKey);\n\n // Add distinct ID to response headers for downstream use\n response.headers.set('x-analytics-distinct-id', distinctId);\n }\n\n // Extract analytics context\n const context = extractAnalyticsContext(request);\n\n // Add context to response headers for server components\n response.headers.set('x-analytics-context', JSON.stringify(context));\n\n // Track the request if edge runtime analytics is available\n if (globalThis.analytics && typeof globalThis.analytics.track === 'function') {\n const eventName = config.getEventName\n ? config.getEventName(pathname, method)\n : getDefaultEventName(pathname, method, config);\n\n const properties = {\n ...context,\n ...(config.getProperties ? config.getProperties(request) : {}),\n pathname,\n method,\n search_params: Object.fromEntries(searchParams.entries()),\n timestamp: new Date().toISOString(),\n };\n\n // Track asynchronously without blocking response\n // Use async IIFE to properly handle the promise\n void (async () => {\n try {\n // Re-check analytics exists inside async context for TypeScript\n if (globalThis.analytics && typeof globalThis.analytics.track === 'function') {\n await globalThis.analytics.track(eventName, properties);\n }\n } catch {\n // Silently fail to avoid disrupting request\n }\n })();\n }\n } catch {\n // Don't let analytics errors break the app\n if (config.debug) {\n // Log error in debug mode only\n }\n }\n\n return response;\n };\n}\n\n/**\n * Ensure distinct ID exists for PostHog tracking\n */\nasync function ensureDistinctId(\n request: MiddlewareRequest,\n response: MiddlewareResponse,\n apiKey: string,\n): Promise<string> {\n // Try to get existing distinct ID from cookies\n const existingId = getDistinctIdFromCookies(request.cookies as any, apiKey);\n\n if (existingId) {\n return existingId;\n }\n\n // Generate new distinct ID\n const newId = generateDistinctId();\n\n // Set cookie with appropriate options\n const cookieName = `ph_${apiKey}_posthog`;\n response.cookies.set(cookieName, JSON.stringify({ distinct_id: newId }), {\n httpOnly: false, // PostHog JS needs to read this\n maxAge: 365 * 24 * 60 * 60, // 1 year\n path: '/',\n sameSite: 'lax',\n secure: process.env.NODE_ENV === 'production',\n });\n\n return newId;\n}\n\n/**\n * Check if route should be tracked\n */\nfunction shouldTrackRoute(pathname: string, config: AnalyticsMiddlewareConfig): boolean {\n // Use custom matcher if provided\n if (config.shouldTrack) {\n return config.shouldTrack(pathname);\n }\n\n // Check exclude routes\n if (config.excludeRoutes) {\n for (const exclude of config.excludeRoutes) {\n if (typeof exclude === 'string') {\n if (pathname.startsWith(exclude)) {\n return false;\n }\n } else if (exclude instanceof RegExp && exclude.test(pathname)) {\n return false;\n }\n }\n }\n\n // Default exclusions\n const defaultExcludes = [\n '/_next/',\n '/favicon.ico',\n '/robots.txt',\n '/sitemap.xml',\n '/.well-known/',\n ];\n\n for (const exclude of defaultExcludes) {\n if (pathname.startsWith(exclude)) {\n return false;\n }\n }\n\n // Check if we should track this type of route\n const isApiRoute = pathname.startsWith('/api/');\n\n if (isApiRoute && config.trackApiRoutes === false) {\n return false;\n }\n\n if (!isApiRoute && config.trackPageViews === false) {\n return false;\n }\n\n return true;\n}\n\n/**\n * Extract analytics context from request\n */\nfunction extractAnalyticsContext(request: MiddlewareRequest): Record<string, any> {\n const { headers } = request;\n\n return {\n // User agent info\n user_agent: headers.get('user-agent') ?? undefined,\n\n // Referrer info\n referer: headers.get('referer') ?? undefined,\n referrer: headers.get('referrer') ?? undefined,\n\n // IP and location info (if available)\n ip:\n headers.get('x-forwarded-for')?.split(',')[0]?.trim() ??\n headers.get('x-real-ip') ??\n undefined,\n\n city: headers.get('x-vercel-ip-city') ?? undefined,\n country: headers.get('x-vercel-ip-country') ?? undefined,\n region: headers.get('x-vercel-ip-country-region') ?? undefined,\n\n // Request info\n host: headers.get('host') ?? undefined,\n protocol: headers.get('x-forwarded-proto') ?? 'https',\n\n accept_encoding: headers.get('accept-encoding') ?? undefined,\n // Accept headers\n accept_language: headers.get('accept-language') ?? undefined,\n\n deployment_id: headers.get('x-vercel-deployment-id') ?? undefined,\n // Edge runtime info\n edge_region: headers.get('x-vercel-edge-region') ?? undefined,\n };\n}\n\n/**\n * Get default event name based on route type\n */\nfunction getDefaultEventName(\n pathname: string,\n method: string,\n _config: AnalyticsMiddlewareConfig,\n): string {\n const isApiRoute = pathname.startsWith('/api/');\n\n if (isApiRoute) {\n return `API ${method} Request`;\n }\n\n return 'Page View';\n}\n\n/**\n * Middleware configuration helper for common patterns (framework-agnostic)\n * Note: createResponse must be provided by the framework-specific wrapper\n */\nexport function createAnalyticsMiddlewareConfig(options: {\n createResponse: () => MiddlewareResponse;\n posthogApiKey?: string;\n segmentWriteKey?: string;\n excludeRoutes?: string[] | RegExp[];\n debug?: boolean;\n}): AnalyticsMiddlewareConfig {\n const config: AnalyticsMiddlewareConfig = {\n analytics: {\n providers: {},\n },\n createResponse: options.createResponse,\n ...(options.debug !== undefined && { debug: options.debug }),\n ...(options.excludeRoutes !== undefined && { excludeRoutes: options.excludeRoutes }),\n ...(options.posthogApiKey !== undefined && { posthogApiKey: options.posthogApiKey }),\n trackApiRoutes: true,\n trackPageViews: true,\n };\n\n // Add providers based on configuration\n if (options.posthogApiKey) {\n config.analytics.providers.posthog = {\n apiKey: options.posthogApiKey,\n };\n }\n\n if (options.segmentWriteKey) {\n config.analytics.providers.segment = {\n writeKey: options.segmentWriteKey,\n };\n }\n\n return config;\n}\n\n/**\n * Extract analytics context from headers (framework-agnostic)\n */\nexport function getAnalyticsContextFromHeaders(headers: Headers): Record<string, any> {\n const contextHeader = headers.get('x-analytics-context');\n\n if (!contextHeader) {\n return {};\n }\n\n try {\n return JSON.parse(contextHeader);\n } catch {\n return {};\n }\n}\n\n/**\n * Get distinct ID from headers (for server components)\n */\nexport function getDistinctIdFromHeaders(headers: Headers): string | null {\n return headers.get('x-analytics-distinct-id');\n}\n\n/**\n * Conditional middleware helper\n */\nexport function conditionalAnalyticsMiddleware(\n config: AnalyticsMiddlewareConfig,\n condition: (request: MiddlewareRequest) => boolean,\n) {\n const middleware = createAnalyticsMiddleware(config);\n\n return async function (request: MiddlewareRequest): Promise<MiddlewareResponse> {\n if (condition(request)) {\n return middleware(request);\n }\n return config.createResponse();\n };\n}\n\n/**\n * Compose multiple middleware functions\n */\nexport function composeMiddleware(\n ...middlewares: ((\n request: MiddlewareRequest,\n createResponse?: () => MiddlewareResponse,\n ) => Promise<MiddlewareResponse>)[]\n) {\n return async function composedMiddleware(\n request: MiddlewareRequest,\n createResponse: () => MiddlewareResponse,\n ): Promise<MiddlewareResponse> {\n let response = createResponse();\n\n for (const middleware of middlewares) {\n response = await middleware(request, createResponse);\n\n // If middleware returns a redirect or error, stop processing\n if (response.status !== 200 || response.headers.get('location')) {\n return response;\n }\n }\n\n return response;\n };\n}\n\n// Type declaration for edge runtime global analytics\ndeclare global {\n var analytics:\n | {\n track: (event: string, properties?: any) => Promise<void>;\n identify: (userId: string, traits?: any) => Promise<void>;\n page: (name?: string, properties?: any) => Promise<void>;\n }\n | undefined;\n}\n"],"mappings":"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"}
@@ -0,0 +1,10 @@
1
+ import { C as EmitterPagePayload, D as EmitterTrackPayload, S as EmitterOptions, b as EmitterIdentifyPayload, c as ProviderConfig, d as TrackingOptions, g as EmitterContext, i as AnalyticsProvider, n as AnalyticsContext, p as EmitterAliasPayload, r as AnalyticsManager, t as AnalyticsConfig, u as ProviderRegistry, v as EmitterGroupPayload, w as EmitterPayload } from "./types-BxBnNQ0V.mjs";
2
+ import { a as screen, i as page, n as group, o as track, r as identify, t as alias } from "./emitters-DldkVSPp.mjs";
3
+ import { a as ContextBuilder, c as createAnonymousSession, d as isGroupPayload, f as isIdentifyPayload, g as withUTM, h as withMetadata, l as createUserSession, m as isTrackPayload, n as createMinimalBootstrapData, o as EventBatch, p as isPagePayload, r as generateDistinctId, s as PayloadBuilder, t as createBootstrapData, u as isAliasPayload } from "./posthog-bootstrap-DWxFrxlt.mjs";
4
+ import { d as EcommerceEventSpec, m as OrderProperties, p as ExtendedProductProperties, r as CartProperties, t as BaseProductProperties } from "./types-CBvxUEaF.mjs";
5
+ import { t as index_d_exports } from "./index-jPzXRn52.mjs";
6
+ import { a as createEmitterProcessor, i as validateConfig, n as createConfigBuilder, o as processEmitterPayload, r as getAnalyticsConfig, s as trackEcommerceEvent, t as PROVIDER_REQUIREMENTS } from "./config-DPS6bSYo.mjs";
7
+ import { a as ConsoleConfig, c as PostHogConfig, i as SegmentOptions, l as PostHogOptions, n as VercelOptions, o as ConsoleOptions, r as SegmentConfig, s as BootstrapData, t as VercelConfig } from "./vercel-types-lwakUfoI.mjs";
8
+ import { n as createAnalyticsManager, t as AnalyticsManager$1 } from "./manager-DvRRjza6.mjs";
9
+ import { a as createIngestionService, c as IngestionErrorResponse, d as validateAnalyticsConfig, f as validateConfigOrThrow, h as createServerAnalyticsUninitialized, i as IngestionServiceConfig, l as IngestionSuccessResponse, m as createServerAnalytics, n as IngestionMetrics, o as validateBatchPayload, p as validateProvider, r as IngestionService, s as validateEventPayload, t as IngestionContext, u as debugConfig } from "./index-BfNWgfa5.mjs";
10
+ export { AnalyticsConfig, AnalyticsContext, AnalyticsManager, AnalyticsManager$1 as AnalyticsManagerClass, AnalyticsProvider, BaseProductProperties, BootstrapData, CartProperties, ConsoleConfig, ConsoleOptions, ContextBuilder, EcommerceEventSpec, EmitterAliasPayload, EmitterContext, EmitterGroupPayload, EmitterIdentifyPayload, EmitterOptions, EmitterPagePayload, EmitterPayload, EmitterTrackPayload, EventBatch, ExtendedProductProperties, type IngestionContext, type IngestionErrorResponse, type IngestionMetrics, IngestionService, type IngestionServiceConfig, type IngestionSuccessResponse, OrderProperties, PROVIDER_REQUIREMENTS, PayloadBuilder, PostHogConfig, PostHogOptions, ProviderConfig, ProviderRegistry, SegmentConfig, SegmentOptions, TrackingOptions, VercelConfig, VercelOptions, alias, createAnalyticsManager, createAnonymousSession, createBootstrapData, createConfigBuilder, createEmitterProcessor, createIngestionService, createMinimalBootstrapData, createServerAnalytics, createServerAnalyticsUninitialized, createUserSession, debugConfig, index_d_exports as ecommerce, generateDistinctId, getAnalyticsConfig, group, identify, isAliasPayload, isGroupPayload, isIdentifyPayload, isPagePayload, isTrackPayload, page, processEmitterPayload, screen, track, trackEcommerceEvent, validateAnalyticsConfig, validateBatchPayload, validateConfig, validateConfigOrThrow, validateEventPayload, validateProvider, withMetadata, withUTM };
@@ -0,0 +1,7 @@
1
+ import { _ as AnalyticsManager, a as ContextBuilder, c as createAnonymousSession, d as isGroupPayload, f as isIdentifyPayload, g as withUTM, h as withMetadata, l as createUserSession, m as isTrackPayload, n as createMinimalBootstrapData, o as EventBatch, p as isPagePayload, r as generateDistinctId, s as PayloadBuilder, t as createBootstrapData, u as isAliasPayload, v as createAnalyticsManager } from "./posthog-bootstrap-CYfIy_WS.mjs";
2
+ import { a as screen, i as page, n as group, o as track, r as identify, t as alias } from "./emitters-6-nKo8i-.mjs";
3
+ import { t as ecommerce_exports } from "./ecommerce-Cgu4wlux.mjs";
4
+ import { a as createEmitterProcessor, i as validateConfig, n as createConfigBuilder, o as processEmitterPayload, r as getAnalyticsConfig, s as trackEcommerceEvent, t as PROVIDER_REQUIREMENTS } from "./config-P6P5adJg.mjs";
5
+ import { a as debugConfig, c as validateProvider, i as validateEventPayload, l as createServerAnalytics, n as createIngestionService, o as validateAnalyticsConfig, r as validateBatchPayload, s as validateConfigOrThrow, t as IngestionService, u as createServerAnalyticsUninitialized } from "./service-cYtBBL8x.mjs";
6
+
7
+ export { AnalyticsManager as AnalyticsManagerClass, ContextBuilder, EventBatch, IngestionService, PROVIDER_REQUIREMENTS, PayloadBuilder, alias, createAnalyticsManager, createAnonymousSession, createBootstrapData, createConfigBuilder, createEmitterProcessor, createIngestionService, createMinimalBootstrapData, createServerAnalytics, createServerAnalyticsUninitialized, createUserSession, debugConfig, ecommerce_exports as ecommerce, generateDistinctId, getAnalyticsConfig, group, identify, isAliasPayload, isGroupPayload, isIdentifyPayload, isPagePayload, isTrackPayload, page, processEmitterPayload, screen, track, trackEcommerceEvent, validateAnalyticsConfig, validateBatchPayload, validateConfig, validateConfigOrThrow, validateEventPayload, validateProvider, withMetadata, withUTM };