@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.
- package/README.md +509 -0
- package/dist/ai-YMnynb-t.mjs +3347 -0
- package/dist/ai-YMnynb-t.mjs.map +1 -0
- package/dist/chunk-DQk6qfdC.mjs +18 -0
- package/dist/client-CTzJVFU5.mjs +9 -0
- package/dist/client-CTzJVFU5.mjs.map +1 -0
- package/dist/client-CcFTauAh.mjs +54 -0
- package/dist/client-CcFTauAh.mjs.map +1 -0
- package/dist/client-CeOLjbac.mjs +281 -0
- package/dist/client-CeOLjbac.mjs.map +1 -0
- package/dist/client-D339NFJS.mjs +267 -0
- package/dist/client-D339NFJS.mjs.map +1 -0
- package/dist/client-next.d.mts +62 -0
- package/dist/client-next.d.mts.map +1 -0
- package/dist/client-next.mjs +525 -0
- package/dist/client-next.mjs.map +1 -0
- package/dist/client.d.mts +30 -0
- package/dist/client.d.mts.map +1 -0
- package/dist/client.mjs +186 -0
- package/dist/client.mjs.map +1 -0
- package/dist/config-DPS6bSYo.d.mts +34 -0
- package/dist/config-DPS6bSYo.d.mts.map +1 -0
- package/dist/config-P6P5adJg.mjs +287 -0
- package/dist/config-P6P5adJg.mjs.map +1 -0
- package/dist/console-8bND3mMU.mjs +128 -0
- package/dist/console-8bND3mMU.mjs.map +1 -0
- package/dist/ecommerce-Cgu4wlux.mjs +993 -0
- package/dist/ecommerce-Cgu4wlux.mjs.map +1 -0
- package/dist/emitters-6-nKo8i-.mjs +208 -0
- package/dist/emitters-6-nKo8i-.mjs.map +1 -0
- package/dist/emitters-DldkVSPp.d.mts +12 -0
- package/dist/emitters-DldkVSPp.d.mts.map +1 -0
- package/dist/index-BfNWgfa5.d.mts +1494 -0
- package/dist/index-BfNWgfa5.d.mts.map +1 -0
- package/dist/index-BkIWe--N.d.mts +953 -0
- package/dist/index-BkIWe--N.d.mts.map +1 -0
- package/dist/index-jPzXRn52.d.mts +184 -0
- package/dist/index-jPzXRn52.d.mts.map +1 -0
- package/dist/manager-DvRRjza6.d.mts +76 -0
- package/dist/manager-DvRRjza6.d.mts.map +1 -0
- package/dist/posthog-bootstrap-CYfIy_WS.mjs +1769 -0
- package/dist/posthog-bootstrap-CYfIy_WS.mjs.map +1 -0
- package/dist/posthog-bootstrap-DWxFrxlt.d.mts +81 -0
- package/dist/posthog-bootstrap-DWxFrxlt.d.mts.map +1 -0
- package/dist/providers-http-client.d.mts +37 -0
- package/dist/providers-http-client.d.mts.map +1 -0
- package/dist/providers-http-client.mjs +320 -0
- package/dist/providers-http-client.mjs.map +1 -0
- package/dist/providers-http-server.d.mts +31 -0
- package/dist/providers-http-server.d.mts.map +1 -0
- package/dist/providers-http-server.mjs +297 -0
- package/dist/providers-http-server.mjs.map +1 -0
- package/dist/providers-http.d.mts +46 -0
- package/dist/providers-http.d.mts.map +1 -0
- package/dist/providers-http.mjs +4 -0
- package/dist/server-edge.d.mts +9 -0
- package/dist/server-edge.d.mts.map +1 -0
- package/dist/server-edge.mjs +373 -0
- package/dist/server-edge.mjs.map +1 -0
- package/dist/server-next.d.mts +67 -0
- package/dist/server-next.d.mts.map +1 -0
- package/dist/server-next.mjs +193 -0
- package/dist/server-next.mjs.map +1 -0
- package/dist/server.d.mts +10 -0
- package/dist/server.mjs +7 -0
- package/dist/service-cYtBBL8x.mjs +945 -0
- package/dist/service-cYtBBL8x.mjs.map +1 -0
- package/dist/shared.d.mts +16 -0
- package/dist/shared.d.mts.map +1 -0
- package/dist/shared.mjs +93 -0
- package/dist/shared.mjs.map +1 -0
- package/dist/types-BxBnNQ0V.d.mts +354 -0
- package/dist/types-BxBnNQ0V.d.mts.map +1 -0
- package/dist/types-CBvxUEaF.d.mts +216 -0
- package/dist/types-CBvxUEaF.d.mts.map +1 -0
- package/dist/types.d.mts +4 -0
- package/dist/types.mjs +0 -0
- package/dist/vercel-types-lwakUfoI.d.mts +102 -0
- package/dist/vercel-types-lwakUfoI.d.mts.map +1 -0
- package/package.json +129 -0
- package/src/client/index.ts +164 -0
- package/src/client/manager.ts +71 -0
- package/src/client/next/components.tsx +270 -0
- package/src/client/next/hooks.ts +217 -0
- package/src/client/next/manager.ts +141 -0
- package/src/client/next.ts +144 -0
- package/src/client-next.ts +101 -0
- package/src/client.ts +89 -0
- package/src/examples/ai-sdk-patterns.ts +583 -0
- package/src/examples/emitter-patterns.ts +476 -0
- package/src/examples/nextjs-emitter-patterns.tsx +403 -0
- package/src/next/app-router.tsx +564 -0
- package/src/next/client.ts +419 -0
- package/src/next/index.ts +84 -0
- package/src/next/middleware.ts +429 -0
- package/src/next/rsc.tsx +300 -0
- package/src/next/server.ts +253 -0
- package/src/next/types.d.ts +220 -0
- package/src/providers/base-provider.ts +419 -0
- package/src/providers/console/client.ts +10 -0
- package/src/providers/console/index.ts +152 -0
- package/src/providers/console/server.ts +6 -0
- package/src/providers/console/types.ts +15 -0
- package/src/providers/http/client.ts +464 -0
- package/src/providers/http/index.ts +30 -0
- package/src/providers/http/server.ts +396 -0
- package/src/providers/http/types.ts +135 -0
- package/src/providers/posthog/client.ts +518 -0
- package/src/providers/posthog/index.ts +11 -0
- package/src/providers/posthog/server.ts +329 -0
- package/src/providers/posthog/types.ts +104 -0
- package/src/providers/segment/client.ts +113 -0
- package/src/providers/segment/index.ts +11 -0
- package/src/providers/segment/server.ts +115 -0
- package/src/providers/segment/types.ts +51 -0
- package/src/providers/vercel/client.ts +102 -0
- package/src/providers/vercel/index.ts +11 -0
- package/src/providers/vercel/server.ts +89 -0
- package/src/providers/vercel/types.ts +27 -0
- package/src/server/index.ts +103 -0
- package/src/server/manager.ts +62 -0
- package/src/server/next.ts +210 -0
- package/src/server-edge.ts +442 -0
- package/src/server-next.ts +39 -0
- package/src/server.ts +106 -0
- package/src/shared/emitters/ai/README.md +981 -0
- package/src/shared/emitters/ai/events/agent.ts +130 -0
- package/src/shared/emitters/ai/events/artifacts.ts +167 -0
- package/src/shared/emitters/ai/events/chat.ts +126 -0
- package/src/shared/emitters/ai/events/chatbot-ecommerce.ts +133 -0
- package/src/shared/emitters/ai/events/completion.ts +103 -0
- package/src/shared/emitters/ai/events/content-generation.ts +347 -0
- package/src/shared/emitters/ai/events/conversation.ts +332 -0
- package/src/shared/emitters/ai/events/product-features.ts +1402 -0
- package/src/shared/emitters/ai/events/streaming.ts +114 -0
- package/src/shared/emitters/ai/events/tool.ts +93 -0
- package/src/shared/emitters/ai/index.ts +69 -0
- package/src/shared/emitters/ai/track-ai-sdk.ts +74 -0
- package/src/shared/emitters/ai/track-ai.ts +50 -0
- package/src/shared/emitters/ai/types.ts +1041 -0
- package/src/shared/emitters/ai/utils.ts +468 -0
- package/src/shared/emitters/ecommerce/events/cart-checkout.ts +106 -0
- package/src/shared/emitters/ecommerce/events/coupon.ts +49 -0
- package/src/shared/emitters/ecommerce/events/engagement.ts +61 -0
- package/src/shared/emitters/ecommerce/events/marketplace.ts +119 -0
- package/src/shared/emitters/ecommerce/events/order.ts +199 -0
- package/src/shared/emitters/ecommerce/events/product.ts +205 -0
- package/src/shared/emitters/ecommerce/events/registry.ts +123 -0
- package/src/shared/emitters/ecommerce/events/wishlist-sharing.ts +140 -0
- package/src/shared/emitters/ecommerce/index.ts +46 -0
- package/src/shared/emitters/ecommerce/track-ecommerce.ts +53 -0
- package/src/shared/emitters/ecommerce/types.ts +314 -0
- package/src/shared/emitters/ecommerce/utils.ts +216 -0
- package/src/shared/emitters/emitter-types.ts +974 -0
- package/src/shared/emitters/emitters.ts +292 -0
- package/src/shared/emitters/helpers.ts +419 -0
- package/src/shared/emitters/index.ts +66 -0
- package/src/shared/index.ts +142 -0
- package/src/shared/ingestion/index.ts +66 -0
- package/src/shared/ingestion/schemas.ts +386 -0
- package/src/shared/ingestion/service.ts +628 -0
- package/src/shared/node22-features.ts +848 -0
- package/src/shared/providers/console-provider.ts +160 -0
- package/src/shared/types/base-types.ts +54 -0
- package/src/shared/types/console-types.ts +19 -0
- package/src/shared/types/posthog-types.ts +131 -0
- package/src/shared/types/segment-types.ts +15 -0
- package/src/shared/types/types.ts +397 -0
- package/src/shared/types/vercel-types.ts +19 -0
- package/src/shared/utils/config-client.ts +19 -0
- package/src/shared/utils/config.ts +250 -0
- package/src/shared/utils/emitter-adapter.ts +212 -0
- package/src/shared/utils/manager.test.ts +36 -0
- package/src/shared/utils/manager.ts +1322 -0
- package/src/shared/utils/posthog-bootstrap.ts +136 -0
- package/src/shared/utils/posthog-client-utils.ts +48 -0
- package/src/shared/utils/posthog-next-utils.ts +282 -0
- package/src/shared/utils/posthog-server-utils.ts +210 -0
- package/src/shared/utils/rate-limit.ts +289 -0
- package/src/shared/utils/security.ts +545 -0
- package/src/shared/utils/validation-client.ts +161 -0
- package/src/shared/utils/validation.ts +399 -0
- package/src/shared.ts +155 -0
- package/src/types/index.ts +62 -0
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
import { C as EmitterPagePayload, D as EmitterTrackPayload, M as Properties, S as EmitterOptions, b as EmitterIdentifyPayload, c as ProviderConfig, d as TrackingOptions, g as EmitterContext, 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, 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 } 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 * as react_jsx_runtime0 from "react/jsx-runtime";
|
|
9
|
+
|
|
10
|
+
//#region src/client/next/manager.d.ts
|
|
11
|
+
declare function createNextJSClientAnalytics(config: AnalyticsConfig): Promise<AnalyticsManager>;
|
|
12
|
+
declare function createNextJSClientAnalyticsUninitialized(config: AnalyticsConfig): Promise<AnalyticsManager>;
|
|
13
|
+
//#endregion
|
|
14
|
+
//#region src/client/next/hooks.d.ts
|
|
15
|
+
declare function useAnalytics(config?: AnalyticsConfig): AnalyticsManager | null;
|
|
16
|
+
declare function usePageTracking(options?: {
|
|
17
|
+
trackSearch?: boolean;
|
|
18
|
+
trackParams?: boolean;
|
|
19
|
+
properties?: Record<string, any>;
|
|
20
|
+
skip?: boolean;
|
|
21
|
+
}): void;
|
|
22
|
+
declare function useTrackEvent(): (event: string, properties?: any, options?: TrackingOptions) => void;
|
|
23
|
+
declare function useIdentifyUser(): (userId: string, traits?: any, options?: TrackingOptions) => void;
|
|
24
|
+
declare function resetAnalytics(): void;
|
|
25
|
+
//#endregion
|
|
26
|
+
//#region src/client/next/components.d.ts
|
|
27
|
+
declare function AnalyticsProvider({
|
|
28
|
+
autoPageTracking,
|
|
29
|
+
children,
|
|
30
|
+
config,
|
|
31
|
+
pageTrackingOptions
|
|
32
|
+
}: {
|
|
33
|
+
children: React.ReactNode;
|
|
34
|
+
config: AnalyticsConfig;
|
|
35
|
+
autoPageTracking?: boolean;
|
|
36
|
+
pageTrackingOptions?: Parameters<typeof usePageTracking>[0];
|
|
37
|
+
}): React.ReactElement;
|
|
38
|
+
declare function TrackedButton({
|
|
39
|
+
children,
|
|
40
|
+
eventName,
|
|
41
|
+
onClick,
|
|
42
|
+
properties,
|
|
43
|
+
...props
|
|
44
|
+
}: React.ButtonHTMLAttributes<HTMLButtonElement> & {
|
|
45
|
+
eventName: string;
|
|
46
|
+
properties?: Properties;
|
|
47
|
+
}): react_jsx_runtime0.JSX.Element;
|
|
48
|
+
declare function TrackedLink({
|
|
49
|
+
children,
|
|
50
|
+
eventName,
|
|
51
|
+
href,
|
|
52
|
+
onClick,
|
|
53
|
+
properties,
|
|
54
|
+
...props
|
|
55
|
+
}: React.AnchorHTMLAttributes<HTMLAnchorElement> & {
|
|
56
|
+
eventName: string;
|
|
57
|
+
properties?: Properties;
|
|
58
|
+
}): react_jsx_runtime0.JSX.Element;
|
|
59
|
+
declare function withViewTracking<P extends object>(Component: React.ComponentType<P>, eventName: string, getProperties?: (props: P) => Properties): (props: P) => react_jsx_runtime0.JSX.Element;
|
|
60
|
+
//#endregion
|
|
61
|
+
export { AnalyticsConfig, AnalyticsContext, AnalyticsManager, AnalyticsProvider, BaseProductProperties, BootstrapData, CartProperties, ConsoleConfig, ConsoleOptions, ContextBuilder, EcommerceEventSpec, EmitterAliasPayload, EmitterContext, EmitterGroupPayload, EmitterIdentifyPayload, EmitterOptions, EmitterPagePayload, EmitterPayload, EmitterTrackPayload, EventBatch, ExtendedProductProperties, OrderProperties, PROVIDER_REQUIREMENTS, PayloadBuilder, PostHogConfig, PostHogOptions, ProviderConfig, ProviderRegistry, SegmentConfig, SegmentOptions, TrackedButton, TrackedLink, TrackingOptions, VercelConfig, VercelOptions, alias, createAnonymousSession, createBootstrapData, createConfigBuilder, createEmitterProcessor, createMinimalBootstrapData, createNextJSClientAnalytics, createNextJSClientAnalyticsUninitialized, createUserSession, index_d_exports as ecommerce, generateDistinctId, getAnalyticsConfig, getDistinctIdFromCookies, group, identify, isAliasPayload, isGroupPayload, isIdentifyPayload, isPagePayload, isTrackPayload, page, processEmitterPayload, resetAnalytics, screen, track, trackEcommerceEvent, useAnalytics, useIdentifyUser, usePageTracking, useTrackEvent, validateConfig, withMetadata, withUTM, withViewTracking };
|
|
62
|
+
//# sourceMappingURL=client-next.d.mts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"client-next.d.mts","names":[],"sources":["../src/client/next/manager.ts","../src/client/next/hooks.ts","../src/client/next/components.tsx"],"mappings":";;;;;;;;;;iBAqCsB,2BAAA,CACpB,MAAA,EAAQ,eAAA,GACP,OAAA,CAAQ,gBAAA;AAAA,iBA8DW,wCAAA,CACpB,MAAA,EAAQ,eAAA,GACP,OAAA,CAAQ,gBAAA;;;iBC/CK,YAAA,CAAa,MAAA,GAAS,eAAA,GAAkB,gBAAA;AAAA,iBA+CxC,eAAA,CAAgB,OAAA;EAC9B,WAAA;EACA,WAAA;EACA,UAAA,GAAa,MAAA;EACb,IAAA;AAAA;AAAA,iBAgEc,aAAA,CAAA,IAAa,KAAA,UACM,UAAA,QAAkB,OAAA,GAAY,eAAA;AAAA,iBAqBjD,eAAA,CAAA,IAAe,MAAA,UACK,MAAA,QAAc,OAAA,GAAY,eAAA;AAAA,iBAoB9C,cAAA,CAAA;;;iBC7IA,iBAAA,CAAA;EACd,gBAAA;EACA,QAAA;EACA,MAAA;EACA;AAAA;EAEA,QAAA,EAAU,KAAA,CAAM,SAAA;EAChB,MAAA,EAAQ,eAAA;EACR,gBAAA;EACA,mBAAA,GAAsB,UAAA,QAAkB,eAAA;AAAA,IA2BrB,KAAA,CAAM,YAAA;AAAA,iBA0BX,aAAA,CAAA;EACd,QAAA;EACA,SAAA;EACA,OAAA;EACA,UAAA;EAAA,GACG;AAAA,GACF,KAAA,CAAM,oBAAA,CAAqB,iBAAA;EAC5B,SAAA;EACA,UAAA,GAAa,UAAA;AAAA,IACd,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,iBA0Ce,WAAA,CAAA;EACd,QAAA;EACA,SAAA;EACA,IAAA;EACA,OAAA;EACA,UAAA;EAAA,GACG;AAAA,GACF,KAAA,CAAM,oBAAA,CAAqB,iBAAA;EAC5B,SAAA;EACA,UAAA,GAAa,UAAA;AAAA,IACd,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,iBAsDe,gBAAA,kBAAA,CACd,SAAA,EAAW,KAAA,CAAM,aAAA,CAAc,CAAA,GAC/B,SAAA,UACA,aAAA,IAAiB,KAAA,EAAO,CAAA,KAAM,UAAA,IAEG,KAAA,EAAO,CAAA,KAAC,kBAAA,CAAA,GAAA,CAAA,OAAA"}
|
|
@@ -0,0 +1,525 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
|
|
3
|
+
import { 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";
|
|
4
|
+
import { a as screen, i as page, n as group, o as track, r as identify, t as alias } from "./emitters-6-nKo8i-.mjs";
|
|
5
|
+
import { t as ecommerce_exports } from "./ecommerce-Cgu4wlux.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-P6P5adJg.mjs";
|
|
7
|
+
import { useCallback, useEffect, useRef, useState } from "react";
|
|
8
|
+
import { useParams, usePathname, useRouter, useSearchParams } from "next/navigation";
|
|
9
|
+
import { createClientObservability } from "@od-oneapp/observability/client/next";
|
|
10
|
+
import { jsx } from "react/jsx-runtime";
|
|
11
|
+
|
|
12
|
+
//#region src/client/next/manager.ts
|
|
13
|
+
/**
|
|
14
|
+
* @fileoverview Next.js Client Analytics Manager
|
|
15
|
+
*
|
|
16
|
+
* Next.js client analytics manager with truly dynamic provider loading.
|
|
17
|
+
* Only imports providers that are actually configured to avoid webpack
|
|
18
|
+
* bundling unused dependencies, reducing bundle size.
|
|
19
|
+
*
|
|
20
|
+
* **Features**:
|
|
21
|
+
* - Dynamic provider loading (only configured providers are bundled)
|
|
22
|
+
* - Code splitting via webpack chunks
|
|
23
|
+
* - Lazy initialization support
|
|
24
|
+
* - Next.js App Router optimized
|
|
25
|
+
*
|
|
26
|
+
* @module @od-oneapp/analytics/client/next/manager
|
|
27
|
+
*/
|
|
28
|
+
const logWarn = (_message, _context) => {};
|
|
29
|
+
/**
|
|
30
|
+
* Create a Next.js client analytics instance with runtime provider loading
|
|
31
|
+
* Only imports providers that are actually configured to avoid webpack bundling unused dependencies
|
|
32
|
+
*
|
|
33
|
+
* @example
|
|
34
|
+
* ```typescript
|
|
35
|
+
* const analytics = await createNextJSClientAnalytics({
|
|
36
|
+
* providers: { posthog: { apiKey: process.env.NEXT_PUBLIC_POSTHOG_KEY! } },
|
|
37
|
+
* });
|
|
38
|
+
* await analytics.track('Dashboard Viewed');
|
|
39
|
+
* ```
|
|
40
|
+
*/
|
|
41
|
+
async function createNextJSClientAnalytics(config) {
|
|
42
|
+
const CLIENT_PROVIDERS = {};
|
|
43
|
+
const providerPromises = Object.keys(config.providers).map(async (providerName) => {
|
|
44
|
+
switch (providerName) {
|
|
45
|
+
case "console": {
|
|
46
|
+
const module = await import(
|
|
47
|
+
/* webpackChunkName: "analytics-console" */
|
|
48
|
+
"./client-CTzJVFU5.mjs"
|
|
49
|
+
).then((n) => n.t);
|
|
50
|
+
CLIENT_PROVIDERS.console = (config) => new module.ConsoleProvider(config);
|
|
51
|
+
break;
|
|
52
|
+
}
|
|
53
|
+
case "posthog": {
|
|
54
|
+
const module = await import(
|
|
55
|
+
/* webpackChunkName: "analytics-posthog" */
|
|
56
|
+
"./client-CeOLjbac.mjs"
|
|
57
|
+
);
|
|
58
|
+
CLIENT_PROVIDERS.posthog = (config) => new module.PostHogClientProvider(config);
|
|
59
|
+
break;
|
|
60
|
+
}
|
|
61
|
+
case "segment": {
|
|
62
|
+
const module = await import(
|
|
63
|
+
/* webpackChunkName: "analytics-segment" */
|
|
64
|
+
"./client-D339NFJS.mjs"
|
|
65
|
+
);
|
|
66
|
+
CLIENT_PROVIDERS.segment = (config) => new module.SegmentClientProvider(config);
|
|
67
|
+
break;
|
|
68
|
+
}
|
|
69
|
+
case "vercel": {
|
|
70
|
+
const module = await import(
|
|
71
|
+
/* webpackChunkName: "analytics-vercel" */
|
|
72
|
+
"./client-CcFTauAh.mjs"
|
|
73
|
+
);
|
|
74
|
+
CLIENT_PROVIDERS.vercel = (config) => new module.VercelClientProvider(config);
|
|
75
|
+
break;
|
|
76
|
+
}
|
|
77
|
+
default:
|
|
78
|
+
logWarn("Unknown analytics provider:", { providerName });
|
|
79
|
+
break;
|
|
80
|
+
}
|
|
81
|
+
});
|
|
82
|
+
await Promise.all(providerPromises);
|
|
83
|
+
const manager = createAnalyticsManager(config, CLIENT_PROVIDERS);
|
|
84
|
+
await manager.initialize();
|
|
85
|
+
return manager;
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* Create a Next.js client analytics instance without initializing
|
|
89
|
+
*
|
|
90
|
+
* @example
|
|
91
|
+
* ```typescript
|
|
92
|
+
* const analytics = await createNextJSClientAnalyticsUninitialized(config);
|
|
93
|
+
* // run setup before first event
|
|
94
|
+
* await analytics.initialize();
|
|
95
|
+
* ```
|
|
96
|
+
*/
|
|
97
|
+
async function createNextJSClientAnalyticsUninitialized(config) {
|
|
98
|
+
const CLIENT_PROVIDERS = {};
|
|
99
|
+
const configuredProviders = Object.keys(config.providers);
|
|
100
|
+
for (const providerName of configuredProviders) switch (providerName) {
|
|
101
|
+
case "console": {
|
|
102
|
+
const { ConsoleProvider } = await import("./client-CTzJVFU5.mjs").then((n) => n.t);
|
|
103
|
+
CLIENT_PROVIDERS.console = (config) => new ConsoleProvider(config);
|
|
104
|
+
break;
|
|
105
|
+
}
|
|
106
|
+
case "posthog": {
|
|
107
|
+
const { PostHogClientProvider } = await import("./client-CeOLjbac.mjs");
|
|
108
|
+
CLIENT_PROVIDERS.posthog = (config) => new PostHogClientProvider(config);
|
|
109
|
+
break;
|
|
110
|
+
}
|
|
111
|
+
case "segment": {
|
|
112
|
+
const { SegmentClientProvider } = await import("./client-D339NFJS.mjs");
|
|
113
|
+
CLIENT_PROVIDERS.segment = (config) => new SegmentClientProvider(config);
|
|
114
|
+
break;
|
|
115
|
+
}
|
|
116
|
+
case "vercel": {
|
|
117
|
+
const { VercelClientProvider } = await import("./client-CcFTauAh.mjs");
|
|
118
|
+
CLIENT_PROVIDERS.vercel = (config) => new VercelClientProvider(config);
|
|
119
|
+
break;
|
|
120
|
+
}
|
|
121
|
+
default:
|
|
122
|
+
logWarn("Unknown analytics provider:", { providerName });
|
|
123
|
+
break;
|
|
124
|
+
}
|
|
125
|
+
return createAnalyticsManager(config, CLIENT_PROVIDERS);
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
//#endregion
|
|
129
|
+
//#region src/client/next/hooks.ts
|
|
130
|
+
/**
|
|
131
|
+
* @fileoverview Next.js Client Hooks for Analytics
|
|
132
|
+
*
|
|
133
|
+
* React hooks for integrating analytics into Next.js applications.
|
|
134
|
+
* Provides hooks for accessing analytics instances, tracking events,
|
|
135
|
+
* and automatic page view tracking.
|
|
136
|
+
*
|
|
137
|
+
* **Hooks**:
|
|
138
|
+
* - `useAnalytics()`: Get or create analytics instance
|
|
139
|
+
* - `usePageTracking()`: Automatic page view tracking in App Router
|
|
140
|
+
* - `useTrackEvent()`: Hook for tracking events
|
|
141
|
+
* - `useIdentifyUser()`: Hook for user identification
|
|
142
|
+
* - `resetAnalytics()`: Utility to reset analytics (useful for testing)
|
|
143
|
+
*
|
|
144
|
+
* **Note**: These hooks use Next.js navigation hooks. For framework-agnostic hooks,
|
|
145
|
+
* use the base hooks from './hooks' or './manager'.
|
|
146
|
+
*
|
|
147
|
+
* @module @od-oneapp/analytics/client/next/hooks
|
|
148
|
+
*/
|
|
149
|
+
let globalAnalytics$1 = null;
|
|
150
|
+
/**
|
|
151
|
+
* Hook to get or create analytics instance.
|
|
152
|
+
*
|
|
153
|
+
* @remarks
|
|
154
|
+
* Returns the global analytics instance, creating it if it doesn't exist
|
|
155
|
+
* and config is provided. Returns null if analytics hasn't been initialized.
|
|
156
|
+
*
|
|
157
|
+
* @param config - Optional analytics configuration (only used on first call)
|
|
158
|
+
* @returns Analytics manager instance or null if not initialized
|
|
159
|
+
*
|
|
160
|
+
* @example
|
|
161
|
+
* ```tsx
|
|
162
|
+
* const analytics = useAnalytics(config);
|
|
163
|
+
* useEffect(() => {
|
|
164
|
+
* if (analytics) {
|
|
165
|
+
* analytics.track('ClientReady');
|
|
166
|
+
* }
|
|
167
|
+
* }, [analytics]);
|
|
168
|
+
* ```
|
|
169
|
+
*/
|
|
170
|
+
function useAnalytics(config) {
|
|
171
|
+
const [analytics, setAnalytics] = useState(null);
|
|
172
|
+
useEffect(() => {
|
|
173
|
+
if (!globalAnalytics$1 && config) {
|
|
174
|
+
const initAnalytics = async () => {
|
|
175
|
+
try {
|
|
176
|
+
const instance = await createNextJSClientAnalytics(config);
|
|
177
|
+
globalAnalytics$1 = instance;
|
|
178
|
+
setAnalytics(instance);
|
|
179
|
+
} catch {}
|
|
180
|
+
};
|
|
181
|
+
initAnalytics();
|
|
182
|
+
} else if (globalAnalytics$1 && analytics !== globalAnalytics$1) setTimeout(() => {
|
|
183
|
+
setAnalytics(globalAnalytics$1);
|
|
184
|
+
}, 0);
|
|
185
|
+
}, [config]);
|
|
186
|
+
return analytics;
|
|
187
|
+
}
|
|
188
|
+
/**
|
|
189
|
+
* Hook for automatic page view tracking in App Router.
|
|
190
|
+
*
|
|
191
|
+
* @remarks
|
|
192
|
+
* Automatically tracks page views when the pathname, search params, or route
|
|
193
|
+
* params change. Prevents duplicate tracking for the same page.
|
|
194
|
+
*
|
|
195
|
+
* @param options - Page tracking options
|
|
196
|
+
* @param options.trackSearch - Whether to include search params in tracking (default: false)
|
|
197
|
+
* @param options.trackParams - Whether to include route params in tracking (default: false)
|
|
198
|
+
* @param options.properties - Additional properties to include in page events
|
|
199
|
+
* @param options.skip - Whether to skip tracking (default: false)
|
|
200
|
+
*
|
|
201
|
+
* @example
|
|
202
|
+
* ```tsx
|
|
203
|
+
* usePageTracking({ trackSearch: true, trackParams: true });
|
|
204
|
+
* ```
|
|
205
|
+
*/
|
|
206
|
+
function usePageTracking(options) {
|
|
207
|
+
const pathname = usePathname();
|
|
208
|
+
const searchParams = useSearchParams();
|
|
209
|
+
const params = useParams();
|
|
210
|
+
const tracked = useRef("");
|
|
211
|
+
useEffect(() => {
|
|
212
|
+
if (options?.skip || !globalAnalytics$1) return;
|
|
213
|
+
const searchString = options?.trackSearch ? searchParams.toString() : "";
|
|
214
|
+
const pageKey = `${pathname}${searchString}`;
|
|
215
|
+
if (tracked.current === pageKey) return;
|
|
216
|
+
tracked.current = pageKey;
|
|
217
|
+
const properties = {
|
|
218
|
+
...options?.properties,
|
|
219
|
+
url: window.location.href,
|
|
220
|
+
path: pathname,
|
|
221
|
+
referrer: document.referrer,
|
|
222
|
+
title: document.title
|
|
223
|
+
};
|
|
224
|
+
if (options?.trackSearch) {
|
|
225
|
+
properties.search = searchString;
|
|
226
|
+
properties.search_params = Object.fromEntries(searchParams.entries());
|
|
227
|
+
}
|
|
228
|
+
if (options?.trackParams && params) properties.route_params = params;
|
|
229
|
+
globalAnalytics$1.page(pathname, properties);
|
|
230
|
+
}, [
|
|
231
|
+
pathname,
|
|
232
|
+
searchParams,
|
|
233
|
+
params,
|
|
234
|
+
options?.skip,
|
|
235
|
+
options?.trackSearch,
|
|
236
|
+
options?.trackParams,
|
|
237
|
+
options?.properties
|
|
238
|
+
]);
|
|
239
|
+
}
|
|
240
|
+
/**
|
|
241
|
+
* Hook for tracking events.
|
|
242
|
+
*
|
|
243
|
+
* @remarks
|
|
244
|
+
* Returns a callback function for tracking events. The callback is stable
|
|
245
|
+
* across renders and can be safely used in event handlers.
|
|
246
|
+
*
|
|
247
|
+
* @returns Callback function for tracking events
|
|
248
|
+
*
|
|
249
|
+
* @example
|
|
250
|
+
* ```tsx
|
|
251
|
+
* const track = useTrackEvent();
|
|
252
|
+
* track('CTA Clicked', { label: 'Request Demo' });
|
|
253
|
+
* ```
|
|
254
|
+
*/
|
|
255
|
+
function useTrackEvent() {
|
|
256
|
+
return useCallback((event, properties, options) => {
|
|
257
|
+
if (!globalAnalytics$1) return;
|
|
258
|
+
globalAnalytics$1.track(event, properties, options);
|
|
259
|
+
}, []);
|
|
260
|
+
}
|
|
261
|
+
/**
|
|
262
|
+
* Hook for user identification.
|
|
263
|
+
*
|
|
264
|
+
* @remarks
|
|
265
|
+
* Returns a callback function for identifying users. The callback is stable
|
|
266
|
+
* across renders and can be safely used in event handlers.
|
|
267
|
+
*
|
|
268
|
+
* @returns Callback function for identifying users
|
|
269
|
+
*
|
|
270
|
+
* @example
|
|
271
|
+
* ```tsx
|
|
272
|
+
* const identify = useIdentifyUser();
|
|
273
|
+
* identify(user.id, { plan: user.plan });
|
|
274
|
+
* ```
|
|
275
|
+
*/
|
|
276
|
+
function useIdentifyUser() {
|
|
277
|
+
return useCallback((userId, traits, options) => {
|
|
278
|
+
if (!globalAnalytics$1) return;
|
|
279
|
+
globalAnalytics$1.identify(userId, traits, options);
|
|
280
|
+
}, []);
|
|
281
|
+
}
|
|
282
|
+
/**
|
|
283
|
+
* Utility to reset analytics (useful for testing).
|
|
284
|
+
*
|
|
285
|
+
* @remarks
|
|
286
|
+
* Clears the global analytics instance. Useful in test environments to
|
|
287
|
+
* ensure clean state between tests.
|
|
288
|
+
*
|
|
289
|
+
* @example
|
|
290
|
+
* ```typescript
|
|
291
|
+
* beforeEach(() => {
|
|
292
|
+
* resetAnalytics();
|
|
293
|
+
* });
|
|
294
|
+
* ```
|
|
295
|
+
*/
|
|
296
|
+
function resetAnalytics() {
|
|
297
|
+
globalAnalytics$1 = null;
|
|
298
|
+
}
|
|
299
|
+
|
|
300
|
+
//#endregion
|
|
301
|
+
//#region src/client/next/components.tsx
|
|
302
|
+
/**
|
|
303
|
+
* @fileoverview Next.js Client Components for Analytics
|
|
304
|
+
*
|
|
305
|
+
* React components for integrating analytics into Next.js applications.
|
|
306
|
+
* Provides provider components, tracked UI elements, and higher-order
|
|
307
|
+
* components for automatic event tracking.
|
|
308
|
+
*
|
|
309
|
+
* **Components**:
|
|
310
|
+
* - `AnalyticsProvider`: Provider component for App Router
|
|
311
|
+
* - `TrackedButton`: Button component with automatic click tracking
|
|
312
|
+
* - `TrackedLink`: Link component with automatic click tracking
|
|
313
|
+
* - `withViewTracking`: HOC for tracking component views
|
|
314
|
+
*
|
|
315
|
+
* **Note**: This file uses Next.js hooks. For framework-agnostic components,
|
|
316
|
+
* use the base components or accept navigation functions as parameters.
|
|
317
|
+
*
|
|
318
|
+
* @module @od-oneapp/analytics/client/next/components
|
|
319
|
+
*/
|
|
320
|
+
let globalAnalytics = null;
|
|
321
|
+
let logger = null;
|
|
322
|
+
/**
|
|
323
|
+
* Analytics provider component for App Router.
|
|
324
|
+
*
|
|
325
|
+
* @remarks
|
|
326
|
+
* Wraps your application and provides analytics context to all child components.
|
|
327
|
+
* Automatically initializes analytics and optionally tracks page views.
|
|
328
|
+
*
|
|
329
|
+
* @param props - Component props
|
|
330
|
+
* @param props.children - React children to wrap
|
|
331
|
+
* @param props.config - Analytics configuration
|
|
332
|
+
* @param props.autoPageTracking - Whether to automatically track page views (default: true)
|
|
333
|
+
* @param props.pageTrackingOptions - Options for page tracking
|
|
334
|
+
*
|
|
335
|
+
* @example
|
|
336
|
+
* ```tsx
|
|
337
|
+
* export default function RootLayout({ children }) {
|
|
338
|
+
* return (
|
|
339
|
+
* <AnalyticsProvider
|
|
340
|
+
* config={{
|
|
341
|
+
* providers: {
|
|
342
|
+
* http: { options: { endpoint: process.env.NEXT_PUBLIC_ANALYTICS_ENDPOINT! } }
|
|
343
|
+
* }
|
|
344
|
+
* }}
|
|
345
|
+
* autoPageTracking={true}
|
|
346
|
+
* >
|
|
347
|
+
* {children}
|
|
348
|
+
* </AnalyticsProvider>
|
|
349
|
+
* );
|
|
350
|
+
* }
|
|
351
|
+
* ```
|
|
352
|
+
*/
|
|
353
|
+
function AnalyticsProvider({ autoPageTracking = true, children, config, pageTrackingOptions }) {
|
|
354
|
+
useEffect(() => {
|
|
355
|
+
if (!globalAnalytics) {
|
|
356
|
+
const initAnalytics = async () => {
|
|
357
|
+
try {
|
|
358
|
+
logger ??= await createClientObservability();
|
|
359
|
+
globalAnalytics = await createNextJSClientAnalytics(config);
|
|
360
|
+
} catch (error) {
|
|
361
|
+
if (logger) logger.captureException(error, { message: "Failed to initialize analytics" });
|
|
362
|
+
}
|
|
363
|
+
};
|
|
364
|
+
initAnalytics();
|
|
365
|
+
}
|
|
366
|
+
}, [config]);
|
|
367
|
+
usePageTracking(autoPageTracking ? pageTrackingOptions : { skip: true });
|
|
368
|
+
return children;
|
|
369
|
+
}
|
|
370
|
+
/**
|
|
371
|
+
* Button component with automatic click tracking.
|
|
372
|
+
*
|
|
373
|
+
* @remarks
|
|
374
|
+
* Wraps a standard button element and automatically tracks click events
|
|
375
|
+
* when the button is clicked.
|
|
376
|
+
*
|
|
377
|
+
* @param props - Button props plus tracking props
|
|
378
|
+
* @param props.eventName - Name of the event to track
|
|
379
|
+
* @param props.properties - Additional properties to include in the event
|
|
380
|
+
* @param props.onClick - Optional click handler (tracking happens before this)
|
|
381
|
+
*
|
|
382
|
+
* @example
|
|
383
|
+
* ```tsx
|
|
384
|
+
* <TrackedButton
|
|
385
|
+
* eventName="Sign Up Clicked"
|
|
386
|
+
* properties={{ location: 'header', variant: 'primary' }}
|
|
387
|
+
* onClick={() => router.push('/signup')}
|
|
388
|
+
* >
|
|
389
|
+
* Sign Up
|
|
390
|
+
* </TrackedButton>
|
|
391
|
+
* ```
|
|
392
|
+
*/
|
|
393
|
+
function TrackedButton({ children, eventName, onClick, properties, ...props }) {
|
|
394
|
+
const track = useTrackEvent();
|
|
395
|
+
const handleClick = useCallback((e) => {
|
|
396
|
+
track(eventName, properties);
|
|
397
|
+
onClick?.(e);
|
|
398
|
+
}, [
|
|
399
|
+
track,
|
|
400
|
+
eventName,
|
|
401
|
+
properties,
|
|
402
|
+
onClick
|
|
403
|
+
]);
|
|
404
|
+
return /* @__PURE__ */ jsx("button", {
|
|
405
|
+
type: "button",
|
|
406
|
+
...props,
|
|
407
|
+
onClick: handleClick,
|
|
408
|
+
children
|
|
409
|
+
});
|
|
410
|
+
}
|
|
411
|
+
/**
|
|
412
|
+
* Link component with automatic click tracking.
|
|
413
|
+
*
|
|
414
|
+
* @remarks
|
|
415
|
+
* Wraps a standard anchor element and automatically tracks click events
|
|
416
|
+
* when the link is clicked. Also handles internal navigation for Next.js.
|
|
417
|
+
*
|
|
418
|
+
* @param props - Anchor props plus tracking props
|
|
419
|
+
* @param props.eventName - Name of the event to track
|
|
420
|
+
* @param props.properties - Additional properties to include in the event
|
|
421
|
+
* @param props.href - Link URL
|
|
422
|
+
* @param props.onClick - Optional click handler (tracking happens before this)
|
|
423
|
+
*
|
|
424
|
+
* @example
|
|
425
|
+
* ```tsx
|
|
426
|
+
* <TrackedLink
|
|
427
|
+
* href="/products"
|
|
428
|
+
* eventName="Product Link Clicked"
|
|
429
|
+
* properties={{ linkText: 'View Products' }}
|
|
430
|
+
* >
|
|
431
|
+
* View Products
|
|
432
|
+
* </TrackedLink>
|
|
433
|
+
* ```
|
|
434
|
+
*/
|
|
435
|
+
function TrackedLink({ children, eventName, href, onClick, properties, ...props }) {
|
|
436
|
+
const track = useTrackEvent();
|
|
437
|
+
const router = useRouter();
|
|
438
|
+
const handleClick = useCallback((e) => {
|
|
439
|
+
track(eventName, {
|
|
440
|
+
...properties,
|
|
441
|
+
href,
|
|
442
|
+
link_text: typeof children === "string" ? children : void 0
|
|
443
|
+
});
|
|
444
|
+
if (onClick) onClick(e);
|
|
445
|
+
else if (href && !props.target && href.startsWith("/")) {
|
|
446
|
+
e.preventDefault();
|
|
447
|
+
router.push(href);
|
|
448
|
+
}
|
|
449
|
+
}, [
|
|
450
|
+
track,
|
|
451
|
+
eventName,
|
|
452
|
+
properties,
|
|
453
|
+
href,
|
|
454
|
+
onClick,
|
|
455
|
+
router,
|
|
456
|
+
children,
|
|
457
|
+
props.target
|
|
458
|
+
]);
|
|
459
|
+
return /* @__PURE__ */ jsx("a", {
|
|
460
|
+
...props,
|
|
461
|
+
href,
|
|
462
|
+
onClick: handleClick,
|
|
463
|
+
children
|
|
464
|
+
});
|
|
465
|
+
}
|
|
466
|
+
/**
|
|
467
|
+
* Higher-order component for tracking component views.
|
|
468
|
+
*
|
|
469
|
+
* @remarks
|
|
470
|
+
* Wraps a component and automatically tracks a view event when the component
|
|
471
|
+
* is first rendered. Useful for tracking page sections or feature usage.
|
|
472
|
+
*
|
|
473
|
+
* @param Component - The component to wrap
|
|
474
|
+
* @param eventName - Name of the event to track
|
|
475
|
+
* @param getProperties - Optional function to extract properties from component props
|
|
476
|
+
* @returns Wrapped component with automatic view tracking
|
|
477
|
+
*
|
|
478
|
+
* @example
|
|
479
|
+
* ```tsx
|
|
480
|
+
* const TrackedDashboard = withViewTracking(
|
|
481
|
+
* Dashboard,
|
|
482
|
+
* 'Dashboard Viewed',
|
|
483
|
+
* (props) => ({ userId: props.userId, plan: props.plan })
|
|
484
|
+
* );
|
|
485
|
+
* ```
|
|
486
|
+
*/
|
|
487
|
+
function withViewTracking(Component, eventName, getProperties) {
|
|
488
|
+
return function TrackedComponent(props) {
|
|
489
|
+
const track = useTrackEvent();
|
|
490
|
+
const tracked = useRef(false);
|
|
491
|
+
useEffect(() => {
|
|
492
|
+
if (!tracked.current) {
|
|
493
|
+
tracked.current = true;
|
|
494
|
+
track(eventName, getProperties ? getProperties(props) : {});
|
|
495
|
+
}
|
|
496
|
+
}, [track, props]);
|
|
497
|
+
return /* @__PURE__ */ jsx(Component, { ...props });
|
|
498
|
+
};
|
|
499
|
+
}
|
|
500
|
+
|
|
501
|
+
//#endregion
|
|
502
|
+
//#region src/client-next.ts
|
|
503
|
+
/**
|
|
504
|
+
* @fileoverview Next.js client exports
|
|
505
|
+
*
|
|
506
|
+
* This module provides Next.js-specific client-side analytics functionality.
|
|
507
|
+
* It exports:
|
|
508
|
+
*
|
|
509
|
+
* - **Analytics Managers**: `createNextJSClientAnalytics()`, `createNextJSClientAnalyticsUninitialized()`
|
|
510
|
+
* - **React Hooks**: `useAnalytics()`, `usePageTracking()`, `useTrackEvent()`, `useIdentifyUser()`
|
|
511
|
+
* - **React Components**: `AnalyticsProvider`, `TrackedButton`, `TrackedLink`, `withViewTracking()`
|
|
512
|
+
* - **Emitters**: Type-safe event tracking functions
|
|
513
|
+
* - **Ecommerce Emitters**: Comprehensive ecommerce event tracking
|
|
514
|
+
* - **AI Emitters**: AI product analytics tracking
|
|
515
|
+
* - **Configuration**: Client-safe configuration utilities
|
|
516
|
+
* - **PostHog Utilities**: Bootstrap data and cookie utilities
|
|
517
|
+
*
|
|
518
|
+
* **Usage**: Import from `@od-oneapp/analytics/client/next` for Next.js client components.
|
|
519
|
+
*
|
|
520
|
+
* @module @od-oneapp/analytics/client/next
|
|
521
|
+
*/
|
|
522
|
+
|
|
523
|
+
//#endregion
|
|
524
|
+
export { AnalyticsProvider, ContextBuilder, EventBatch, PROVIDER_REQUIREMENTS, PayloadBuilder, TrackedButton, TrackedLink, alias, createAnonymousSession, createBootstrapData, createConfigBuilder, createEmitterProcessor, createMinimalBootstrapData, createNextJSClientAnalytics, createNextJSClientAnalyticsUninitialized, createUserSession, ecommerce_exports as ecommerce, generateDistinctId, getAnalyticsConfig, getDistinctIdFromCookies, group, identify, isAliasPayload, isGroupPayload, isIdentifyPayload, isPagePayload, isTrackPayload, page, processEmitterPayload, resetAnalytics, screen, track, trackEcommerceEvent, useAnalytics, useIdentifyUser, usePageTracking, useTrackEvent, validateConfig, withMetadata, withUTM, withViewTracking };
|
|
525
|
+
//# sourceMappingURL=client-next.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"client-next.mjs","names":["globalAnalytics"],"sources":["../src/client/next/manager.ts","../src/client/next/hooks.ts","../src/client/next/components.tsx","../src/client-next.ts"],"sourcesContent":["/**\n * @fileoverview Next.js Client Analytics Manager\n *\n * Next.js client analytics manager with truly dynamic provider loading.\n * Only imports providers that are actually configured to avoid webpack\n * bundling unused dependencies, reducing bundle size.\n *\n * **Features**:\n * - Dynamic provider loading (only configured providers are bundled)\n * - Code splitting via webpack chunks\n * - Lazy initialization support\n * - Next.js App Router optimized\n *\n * @module @od-oneapp/analytics/client/next/manager\n */\n\n// Simple console fallback - observability integration can be added later\nimport { createAnalyticsManager } from '../../shared/utils/manager';\n\nimport type { AnalyticsConfig, AnalyticsManager, ProviderRegistry } from '../../shared/types/types';\nconst logWarn = (_message: string, _context?: any) => {\n // No-op to avoid console warnings in production\n // TODO: Add proper error logging via observability package\n};\n\n/**\n * Create a Next.js client analytics instance with runtime provider loading\n * Only imports providers that are actually configured to avoid webpack bundling unused dependencies\n *\n * @example\n * ```typescript\n * const analytics = await createNextJSClientAnalytics({\n * providers: { posthog: { apiKey: process.env.NEXT_PUBLIC_POSTHOG_KEY! } },\n * });\n * await analytics.track('Dashboard Viewed');\n * ```\n */\nexport async function createNextJSClientAnalytics(\n config: AnalyticsConfig,\n): Promise<AnalyticsManager> {\n const CLIENT_PROVIDERS: ProviderRegistry = {};\n\n // Get configured providers\n const configuredProviders = Object.keys(config.providers);\n\n // Only import configured providers using truly dynamic imports\n const providerPromises = configuredProviders.map(async providerName => {\n switch (providerName) {\n case 'console': {\n const module = await import(\n /* webpackChunkName: \"analytics-console\" */ '../../providers/console/client'\n );\n CLIENT_PROVIDERS.console = config => new module.ConsoleProvider(config);\n break;\n }\n case 'posthog': {\n const module = await import(\n /* webpackChunkName: \"analytics-posthog\" */ '../../providers/posthog/client'\n );\n CLIENT_PROVIDERS.posthog = config => new module.PostHogClientProvider(config);\n break;\n }\n case 'segment': {\n const module = await import(\n /* webpackChunkName: \"analytics-segment\" */ '../../providers/segment/client'\n );\n CLIENT_PROVIDERS.segment = config => new module.SegmentClientProvider(config);\n break;\n }\n case 'vercel': {\n const module = await import(\n /* webpackChunkName: \"analytics-vercel\" */ '../../providers/vercel/client'\n );\n CLIENT_PROVIDERS.vercel = config => new module.VercelClientProvider(config);\n break;\n }\n default:\n // Skip unknown providers\n logWarn('Unknown analytics provider:', { providerName });\n break;\n }\n });\n\n // Wait for all configured providers to load\n await Promise.all(providerPromises);\n\n const manager = createAnalyticsManager(config, CLIENT_PROVIDERS);\n await manager.initialize();\n return manager;\n}\n\n/**\n * Create a Next.js client analytics instance without initializing\n *\n * @example\n * ```typescript\n * const analytics = await createNextJSClientAnalyticsUninitialized(config);\n * // run setup before first event\n * await analytics.initialize();\n * ```\n */\nexport async function createNextJSClientAnalyticsUninitialized(\n config: AnalyticsConfig,\n): Promise<AnalyticsManager> {\n const CLIENT_PROVIDERS: ProviderRegistry = {};\n\n // Get configured providers\n const configuredProviders = Object.keys(config.providers);\n\n // Dynamically import only configured providers\n for (const providerName of configuredProviders) {\n switch (providerName) {\n case 'console': {\n const { ConsoleProvider } = await import('../../providers/console/client');\n CLIENT_PROVIDERS.console = config => new ConsoleProvider(config);\n break;\n }\n case 'posthog': {\n const { PostHogClientProvider } = await import('../../providers/posthog/client');\n CLIENT_PROVIDERS.posthog = config => new PostHogClientProvider(config);\n break;\n }\n case 'segment': {\n const { SegmentClientProvider } = await import('../../providers/segment/client');\n CLIENT_PROVIDERS.segment = config => new SegmentClientProvider(config);\n break;\n }\n case 'vercel': {\n const { VercelClientProvider } = await import('../../providers/vercel/client');\n CLIENT_PROVIDERS.vercel = config => new VercelClientProvider(config);\n break;\n }\n default:\n // Skip unknown providers\n logWarn('Unknown analytics provider:', { providerName });\n break;\n }\n }\n\n return createAnalyticsManager(config, CLIENT_PROVIDERS);\n}\n","/**\n * @fileoverview Next.js Client Hooks for Analytics\n *\n * React hooks for integrating analytics into Next.js applications.\n * Provides hooks for accessing analytics instances, tracking events,\n * and automatic page view tracking.\n *\n * **Hooks**:\n * - `useAnalytics()`: Get or create analytics instance\n * - `usePageTracking()`: Automatic page view tracking in App Router\n * - `useTrackEvent()`: Hook for tracking events\n * - `useIdentifyUser()`: Hook for user identification\n * - `resetAnalytics()`: Utility to reset analytics (useful for testing)\n *\n * **Note**: These hooks use Next.js navigation hooks. For framework-agnostic hooks,\n * use the base hooks from './hooks' or './manager'.\n *\n * @module @od-oneapp/analytics/client/next/hooks\n */\n\n'use client';\n\n// Note: These are Next.js hooks required for App Router integration\n// Client components are already Next.js-specific, so this is acceptable\nimport { useCallback, useEffect, useRef, useState } from 'react';\n\nimport { useParams, usePathname, useSearchParams } from 'next/navigation';\n// Type-only imports for Next.js types (compile-time only, no runtime dependency)\n\nimport { createNextJSClientAnalytics } from './manager';\n\nimport type { AnalyticsConfig, AnalyticsManager, TrackingOptions } from '../../shared/types/types';\n\n// Global analytics instance\nlet globalAnalytics: AnalyticsManager | null = null;\n\n/**\n * Hook to get or create analytics instance.\n *\n * @remarks\n * Returns the global analytics instance, creating it if it doesn't exist\n * and config is provided. Returns null if analytics hasn't been initialized.\n *\n * @param config - Optional analytics configuration (only used on first call)\n * @returns Analytics manager instance or null if not initialized\n *\n * @example\n * ```tsx\n * const analytics = useAnalytics(config);\n * useEffect(() => {\n * if (analytics) {\n * analytics.track('ClientReady');\n * }\n * }, [analytics]);\n * ```\n */\nexport function useAnalytics(config?: AnalyticsConfig): AnalyticsManager | null {\n const [analytics, setAnalytics] = useState<AnalyticsManager | null>(null);\n\n useEffect(() => {\n if (!globalAnalytics && config) {\n const initAnalytics = async () => {\n try {\n // Note: Client-side observability handled by manager\n\n const instance = await createNextJSClientAnalytics(config);\n globalAnalytics = instance;\n setAnalytics(instance);\n } catch {\n // Failed to initialize analytics - silently continue\n // TODO: Add proper error logging via observability package\n }\n };\n void initAnalytics();\n } else if (globalAnalytics && analytics !== globalAnalytics) {\n // Use setTimeout to avoid synchronous setState in effect\n setTimeout(() => {\n setAnalytics(globalAnalytics);\n }, 0);\n }\n }, [config]);\n\n return analytics;\n}\n\n/**\n * Hook for automatic page view tracking in App Router.\n *\n * @remarks\n * Automatically tracks page views when the pathname, search params, or route\n * params change. Prevents duplicate tracking for the same page.\n *\n * @param options - Page tracking options\n * @param options.trackSearch - Whether to include search params in tracking (default: false)\n * @param options.trackParams - Whether to include route params in tracking (default: false)\n * @param options.properties - Additional properties to include in page events\n * @param options.skip - Whether to skip tracking (default: false)\n *\n * @example\n * ```tsx\n * usePageTracking({ trackSearch: true, trackParams: true });\n * ```\n */\nexport function usePageTracking(options?: {\n trackSearch?: boolean;\n trackParams?: boolean;\n properties?: Record<string, any>;\n skip?: boolean;\n}) {\n const pathname = usePathname();\n const searchParams = useSearchParams();\n const params = useParams();\n const tracked = useRef<string>('');\n\n useEffect(() => {\n if (options?.skip || !globalAnalytics) return;\n\n // Create unique key for this page view\n const searchString = options?.trackSearch ? searchParams.toString() : '';\n const pageKey = `${pathname}${searchString}`;\n\n // Avoid duplicate tracking\n if (tracked.current === pageKey) return;\n tracked.current = pageKey;\n\n // Build properties\n const properties: Record<string, any> = {\n ...options?.properties,\n url: window.location.href,\n path: pathname,\n referrer: document.referrer,\n title: document.title,\n };\n\n if (options?.trackSearch) {\n properties.search = searchString;\n properties.search_params = Object.fromEntries(searchParams.entries());\n }\n\n if (options?.trackParams && params) {\n properties.route_params = params;\n }\n\n // Track page view\n void globalAnalytics.page(pathname, properties);\n }, [\n pathname,\n searchParams,\n params,\n options?.skip,\n options?.trackSearch,\n options?.trackParams,\n options?.properties,\n ]);\n}\n\n/**\n * Hook for tracking events.\n *\n * @remarks\n * Returns a callback function for tracking events. The callback is stable\n * across renders and can be safely used in event handlers.\n *\n * @returns Callback function for tracking events\n *\n * @example\n * ```tsx\n * const track = useTrackEvent();\n * track('CTA Clicked', { label: 'Request Demo' });\n * ```\n */\nexport function useTrackEvent() {\n return useCallback((event: string, properties?: any, options?: TrackingOptions) => {\n if (!globalAnalytics) return;\n void globalAnalytics.track(event, properties, options);\n }, []);\n}\n\n/**\n * Hook for user identification.\n *\n * @remarks\n * Returns a callback function for identifying users. The callback is stable\n * across renders and can be safely used in event handlers.\n *\n * @returns Callback function for identifying users\n *\n * @example\n * ```tsx\n * const identify = useIdentifyUser();\n * identify(user.id, { plan: user.plan });\n * ```\n */\nexport function useIdentifyUser() {\n return useCallback((userId: string, traits?: any, options?: TrackingOptions) => {\n if (!globalAnalytics) return;\n void globalAnalytics.identify(userId, traits, options);\n }, []);\n}\n\n/**\n * Utility to reset analytics (useful for testing).\n *\n * @remarks\n * Clears the global analytics instance. Useful in test environments to\n * ensure clean state between tests.\n *\n * @example\n * ```typescript\n * beforeEach(() => {\n * resetAnalytics();\n * });\n * ```\n */\nexport function resetAnalytics() {\n globalAnalytics = null;\n}\n","/**\n * @fileoverview Next.js Client Components for Analytics\n *\n * React components for integrating analytics into Next.js applications.\n * Provides provider components, tracked UI elements, and higher-order\n * components for automatic event tracking.\n *\n * **Components**:\n * - `AnalyticsProvider`: Provider component for App Router\n * - `TrackedButton`: Button component with automatic click tracking\n * - `TrackedLink`: Link component with automatic click tracking\n * - `withViewTracking`: HOC for tracking component views\n *\n * **Note**: This file uses Next.js hooks. For framework-agnostic components,\n * use the base components or accept navigation functions as parameters.\n *\n * @module @od-oneapp/analytics/client/next/components\n */\n\n'use client';\n\nimport { useCallback, useEffect, useRef } from 'react';\n\nimport type { Route } from 'next';\n\nimport { createClientObservability } from '@od-oneapp/observability/client/next';\nimport { useRouter } from 'next/navigation';\n\nimport { usePageTracking, useTrackEvent } from './hooks';\nimport { createNextJSClientAnalytics } from './manager';\n\nimport type { AnalyticsConfig, AnalyticsManager, Properties } from '../../shared/types/types';\nimport type { ObservabilityClient } from '@od-oneapp/observability/client/next';\n\n// Global analytics instance\nlet globalAnalytics: AnalyticsManager | null = null;\n\n// Global logger instance (from @od-oneapp/observability)\n// Using minimal interface for optional fallback error logging\n\nlet logger: ObservabilityClient | null = null;\n\n/**\n * Analytics provider component for App Router.\n *\n * @remarks\n * Wraps your application and provides analytics context to all child components.\n * Automatically initializes analytics and optionally tracks page views.\n *\n * @param props - Component props\n * @param props.children - React children to wrap\n * @param props.config - Analytics configuration\n * @param props.autoPageTracking - Whether to automatically track page views (default: true)\n * @param props.pageTrackingOptions - Options for page tracking\n *\n * @example\n * ```tsx\n * export default function RootLayout({ children }) {\n * return (\n * <AnalyticsProvider\n * config={{\n * providers: {\n * http: { options: { endpoint: process.env.NEXT_PUBLIC_ANALYTICS_ENDPOINT! } }\n * }\n * }}\n * autoPageTracking={true}\n * >\n * {children}\n * </AnalyticsProvider>\n * );\n * }\n * ```\n */\nexport function AnalyticsProvider({\n autoPageTracking = true,\n children,\n config,\n pageTrackingOptions,\n}: {\n children: React.ReactNode;\n config: AnalyticsConfig;\n autoPageTracking?: boolean;\n pageTrackingOptions?: Parameters<typeof usePageTracking>[0];\n}) {\n // Initialize analytics\n useEffect(() => {\n if (!globalAnalytics) {\n const initAnalytics = async () => {\n try {\n // Initialize logger if not already initialized\n logger ??= await createClientObservability();\n\n const instance = await createNextJSClientAnalytics(config);\n globalAnalytics = instance;\n } catch (error) {\n if (logger) {\n logger.captureException(error, {\n message: 'Failed to initialize analytics',\n });\n }\n }\n };\n void initAnalytics();\n }\n }, [config]);\n\n // Auto page tracking\n usePageTracking(autoPageTracking ? pageTrackingOptions : { skip: true });\n\n return children as React.ReactElement;\n}\n\n/**\n * Button component with automatic click tracking.\n *\n * @remarks\n * Wraps a standard button element and automatically tracks click events\n * when the button is clicked.\n *\n * @param props - Button props plus tracking props\n * @param props.eventName - Name of the event to track\n * @param props.properties - Additional properties to include in the event\n * @param props.onClick - Optional click handler (tracking happens before this)\n *\n * @example\n * ```tsx\n * <TrackedButton\n * eventName=\"Sign Up Clicked\"\n * properties={{ location: 'header', variant: 'primary' }}\n * onClick={() => router.push('/signup')}\n * >\n * Sign Up\n * </TrackedButton>\n * ```\n */\nexport function TrackedButton({\n children,\n eventName,\n onClick,\n properties,\n ...props\n}: React.ButtonHTMLAttributes<HTMLButtonElement> & {\n eventName: string;\n properties?: Properties;\n}) {\n const track = useTrackEvent();\n\n const handleClick = useCallback(\n (e: React.MouseEvent<HTMLButtonElement>) => {\n track(eventName, properties);\n onClick?.(e);\n },\n [track, eventName, properties, onClick],\n );\n\n return (\n <button type=\"button\" {...props} onClick={handleClick}>\n {children}\n </button>\n );\n}\n\n/**\n * Link component with automatic click tracking.\n *\n * @remarks\n * Wraps a standard anchor element and automatically tracks click events\n * when the link is clicked. Also handles internal navigation for Next.js.\n *\n * @param props - Anchor props plus tracking props\n * @param props.eventName - Name of the event to track\n * @param props.properties - Additional properties to include in the event\n * @param props.href - Link URL\n * @param props.onClick - Optional click handler (tracking happens before this)\n *\n * @example\n * ```tsx\n * <TrackedLink\n * href=\"/products\"\n * eventName=\"Product Link Clicked\"\n * properties={{ linkText: 'View Products' }}\n * >\n * View Products\n * </TrackedLink>\n * ```\n */\nexport function TrackedLink({\n children,\n eventName,\n href,\n onClick,\n properties,\n ...props\n}: React.AnchorHTMLAttributes<HTMLAnchorElement> & {\n eventName: string;\n properties?: Properties;\n}) {\n const track = useTrackEvent();\n const router = useRouter();\n\n const handleClick = useCallback(\n (e: React.MouseEvent<HTMLAnchorElement>) => {\n // Track the event\n const enhancedProperties = {\n ...properties,\n href,\n link_text: typeof children === 'string' ? children : undefined,\n };\n track(eventName, enhancedProperties);\n\n // Handle navigation\n if (onClick) {\n onClick(e);\n } else if (href && !props.target && href.startsWith('/')) {\n // Internal navigation\n e.preventDefault();\n router.push(href as Route);\n }\n },\n [track, eventName, properties, href, onClick, router, children, props.target],\n );\n\n return (\n <a {...props} href={href} onClick={handleClick}>\n {children}\n </a>\n );\n}\n\n/**\n * Higher-order component for tracking component views.\n *\n * @remarks\n * Wraps a component and automatically tracks a view event when the component\n * is first rendered. Useful for tracking page sections or feature usage.\n *\n * @param Component - The component to wrap\n * @param eventName - Name of the event to track\n * @param getProperties - Optional function to extract properties from component props\n * @returns Wrapped component with automatic view tracking\n *\n * @example\n * ```tsx\n * const TrackedDashboard = withViewTracking(\n * Dashboard,\n * 'Dashboard Viewed',\n * (props) => ({ userId: props.userId, plan: props.plan })\n * );\n * ```\n */\nexport function withViewTracking<P extends object>(\n Component: React.ComponentType<P>,\n eventName: string,\n getProperties?: (props: P) => Properties,\n) {\n return function TrackedComponent(props: P) {\n const track = useTrackEvent();\n const tracked = useRef(false);\n\n useEffect(() => {\n if (!tracked.current) {\n tracked.current = true;\n const properties = getProperties ? getProperties(props) : {};\n track(eventName, properties);\n }\n }, [track, props]);\n\n return <Component {...props} />;\n };\n}\n","/**\n * @fileoverview Next.js client exports\n *\n * This module provides Next.js-specific client-side analytics functionality.\n * It exports:\n *\n * - **Analytics Managers**: `createNextJSClientAnalytics()`, `createNextJSClientAnalyticsUninitialized()`\n * - **React Hooks**: `useAnalytics()`, `usePageTracking()`, `useTrackEvent()`, `useIdentifyUser()`\n * - **React Components**: `AnalyticsProvider`, `TrackedButton`, `TrackedLink`, `withViewTracking()`\n * - **Emitters**: Type-safe event tracking functions\n * - **Ecommerce Emitters**: Comprehensive ecommerce event tracking\n * - **AI Emitters**: AI product analytics tracking\n * - **Configuration**: Client-safe configuration utilities\n * - **PostHog Utilities**: Bootstrap data and cookie utilities\n *\n * **Usage**: Import from `@od-oneapp/analytics/client/next` for Next.js client components.\n *\n * @module @od-oneapp/analytics/client/next\n */\n\n'use client';\n\n// Export Next.js specific analytics manager\nexport {\n createNextJSClientAnalytics,\n createNextJSClientAnalyticsUninitialized,\n} from './client/next/manager';\n\n// Export Next.js hooks\nexport {\n resetAnalytics,\n useAnalytics,\n useIdentifyUser,\n usePageTracking,\n useTrackEvent,\n} from './client/next/hooks';\n\n// Export Next.js components\nexport {\n AnalyticsProvider,\n TrackedButton,\n TrackedLink,\n withViewTracking,\n} from './client/next/components';\n\n// Export all emitters - these are the preferred way to track events\nexport {\n // Emitter utilities\n ContextBuilder,\n EventBatch,\n PayloadBuilder,\n alias,\n createAnonymousSession,\n createUserSession,\n // Ecommerce emitters namespace\n ecommerce,\n group,\n // Core Segment.io spec emitters\n identify,\n isAliasPayload,\n isGroupPayload,\n isIdentifyPayload,\n isPagePayload,\n // Type guards\n isTrackPayload,\n page,\n screen,\n track,\n withMetadata,\n withUTM,\n} from './shared/emitters';\n\n// Export adapter utilities\nexport {\n createEmitterProcessor,\n // Emitter processing utilities\n processEmitterPayload,\n trackEcommerceEvent,\n} from './shared/utils/emitter-adapter';\n\n// Export client-safe configuration utilities\nexport {\n PROVIDER_REQUIREMENTS,\n createConfigBuilder,\n getAnalyticsConfig,\n validateConfig,\n} from './shared/utils/config-client';\n\n// Validation utilities removed - validation should happen on the server side only\n// This follows the four-file export pattern to avoid importing server-only dependencies\n\n// Export PostHog utilities\nexport {\n createBootstrapData,\n createMinimalBootstrapData,\n generateDistinctId,\n getDistinctIdFromCookies,\n} from './shared/utils/posthog-bootstrap';\n\n// Export types\nexport type * from './types';\n"],"mappings":"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"}
|