@macroui/event-tracker 1.3.0 → 1.3.1

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 (69) hide show
  1. package/dist/event-tracker.cjs +4252 -879
  2. package/dist/event-tracker.cjs.map +1 -0
  3. package/dist/event-tracker.js +4252 -879
  4. package/dist/event-tracker.js.map +1 -0
  5. package/dist/event-tracker.min.js +2 -1
  6. package/dist/event-tracker.min.js.map +1 -0
  7. package/dist/event-tracker.mjs +4212 -880
  8. package/dist/event-tracker.mjs.map +1 -0
  9. package/dist/plugin/debug-sender.cjs +53 -2
  10. package/dist/plugin/debug-sender.mjs +53 -2
  11. package/dist/plugin/experiment.cjs +181 -0
  12. package/dist/plugin/experiment.cjs.map +1 -0
  13. package/dist/plugin/experiment.mjs +178 -0
  14. package/dist/plugin/experiment.mjs.map +1 -0
  15. package/dist/plugin/indexeddb-sender.cjs +51 -2
  16. package/dist/plugin/indexeddb-sender.mjs +51 -2
  17. package/dist/plugin/otel-bridge.cjs +164 -0
  18. package/dist/plugin/otel-bridge.cjs.map +1 -0
  19. package/dist/plugin/otel-bridge.mjs +162 -0
  20. package/dist/plugin/otel-bridge.mjs.map +1 -0
  21. package/dist/plugin/predictive-batcher.cjs +61 -0
  22. package/dist/plugin/predictive-batcher.cjs.map +1 -0
  23. package/dist/plugin/predictive-batcher.mjs +58 -0
  24. package/dist/plugin/predictive-batcher.mjs.map +1 -0
  25. package/dist/plugin/webview-bridge.cjs +83 -31
  26. package/dist/plugin/webview-bridge.mjs +83 -31
  27. package/dist/stats.cjs +148 -0
  28. package/dist/stats.cjs.map +1 -0
  29. package/dist/stats.mjs +145 -0
  30. package/dist/stats.mjs.map +1 -0
  31. package/dist/types/core/env.d.ts +2 -0
  32. package/dist/types/core/failed-queue.d.ts +19 -2
  33. package/dist/types/core/idle.d.ts +23 -0
  34. package/dist/types/core/payload-signer.d.ts +31 -0
  35. package/dist/types/core/pii.d.ts +46 -0
  36. package/dist/types/core/platform.d.ts +23 -0
  37. package/dist/types/core/privacy.d.ts +42 -0
  38. package/dist/types/core/replay.d.ts +41 -0
  39. package/dist/types/core/retry-policy.d.ts +11 -8
  40. package/dist/types/core/send-pipeline.d.ts +5 -1
  41. package/dist/types/core/stats.d.ts +77 -0
  42. package/dist/types/core/tracker.d.ts +7 -1
  43. package/dist/types/core/wasm-crypto.d.ts +28 -0
  44. package/dist/types/edge/index.d.ts +41 -0
  45. package/dist/types/federation.d.ts +34 -0
  46. package/dist/types/index.d.ts +42 -1
  47. package/dist/types/plugins/audience-sync/index.d.ts +67 -0
  48. package/dist/types/plugins/cross-domain/index.d.ts +20 -0
  49. package/dist/types/plugins/csp-compliant/index.d.ts +17 -0
  50. package/dist/types/plugins/experiment/index.d.ts +43 -0
  51. package/dist/types/plugins/otel-bridge/index.d.ts +22 -0
  52. package/dist/types/plugins/otel-exporter/index.d.ts +50 -0
  53. package/dist/types/plugins/pii-detector/index.d.ts +8 -0
  54. package/dist/types/plugins/predictive-batcher/index.d.ts +29 -0
  55. package/dist/types/plugins/privacy/index.d.ts +19 -0
  56. package/dist/types/plugins/rate-limiter/index.d.ts +41 -0
  57. package/dist/types/plugins/schema-registry/index.d.ts +41 -0
  58. package/dist/types/plugins/webview-bridge/index.d.ts +33 -9
  59. package/dist/types/send/ajax-sender.d.ts +6 -1
  60. package/dist/types/send/batch-sender.d.ts +12 -1
  61. package/dist/types/send/encode.d.ts +13 -1
  62. package/dist/types/send/offscreen-sender.d.ts +25 -0
  63. package/dist/types/send/sender.d.ts +20 -3
  64. package/dist/types/send/ws-sender.d.ts +38 -0
  65. package/dist/types/types/config.d.ts +17 -1
  66. package/dist/types/types/index.d.ts +1 -1
  67. package/package.json +1 -1
  68. package/dist/types/types.test-d.d.ts +0 -5
  69. package/dist/types.test-d.ts +0 -103
@@ -0,0 +1,77 @@
1
+ /**
2
+ * Sender 失败统计(v1.2.0)
3
+ *
4
+ * - 每个 sender 维护 attempts / success / failure / total_duration
5
+ * - SDK 全局汇总
6
+ * - 用户可 sdk.getStats() 查
7
+ * - 自动每 60s 输出到 console(debug 模式)
8
+ */
9
+ export interface SenderStat {
10
+ /** sender 名称(image / beacon / ajax / batch) */
11
+ name: string;
12
+ /** 尝试次数 */
13
+ attempts: number;
14
+ /** 成功次数 */
15
+ success: number;
16
+ /** 失败次数 */
17
+ failure: number;
18
+ /** 累计耗时(ms) */
19
+ total_duration: number;
20
+ /** 平均耗时(ms) */
21
+ avg_duration: number;
22
+ /** 最大单次耗时(ms) */
23
+ max_duration: number;
24
+ /** 最近一次失败原因 */
25
+ last_error?: string;
26
+ /** 最近一次失败时间戳 */
27
+ last_error_at?: number;
28
+ }
29
+ export interface StatsSnapshot {
30
+ /** SDK 启动后累计发送次数 */
31
+ total: number;
32
+ /** 成功累计 */
33
+ success: number;
34
+ /** 失败累计 */
35
+ failure: number;
36
+ /** 重试累计 */
37
+ retry: number;
38
+ /** in-flight(当前未完成) */
39
+ in_flight: number;
40
+ /** flush 累计 */
41
+ flush_count: number;
42
+ /** 上次 flush 时间 */
43
+ last_flush_at?: number;
44
+ /** 每个 sender 统计 */
45
+ by_sender: Record<string, SenderStat>;
46
+ /** 时间戳 */
47
+ taken_at: number;
48
+ }
49
+ export declare class StatsCollector {
50
+ private total;
51
+ private success;
52
+ private failure;
53
+ private retry;
54
+ private in_flight;
55
+ private flushCount;
56
+ private lastFlushAt?;
57
+ private bySender;
58
+ /** 记录一次发送开始 */
59
+ recordStart(senderName: string): number;
60
+ /** 记录一次发送成功 */
61
+ recordSuccess(senderName: string, startTs: number): void;
62
+ /** 记录一次发送失败 */
63
+ recordFailure(senderName: string, startTs: number, err: Error): void;
64
+ /** 记录一次重试 */
65
+ recordRetry(): void;
66
+ /** 记录一次 flush */
67
+ recordFlush(): void;
68
+ /** 拍快照 */
69
+ snapshot(): StatsSnapshot;
70
+ /** 重置 */
71
+ reset(): void;
72
+ /** 列出所有 sender 名 */
73
+ listSenders(): string[];
74
+ private getOrCreate;
75
+ }
76
+ /** 全局单例 */
77
+ export declare const GLOBAL_STATS: StatsCollector;
@@ -32,6 +32,8 @@ export declare class EventTracker {
32
32
  private _channel;
33
33
  private _pipeline;
34
34
  private _signedIdentity?;
35
+ private _stats;
36
+ private _statsTimer;
35
37
  private _inited;
36
38
  readonly instanceId: string;
37
39
  constructor();
@@ -103,7 +105,7 @@ export declare class EventTracker {
103
105
  waitUntilIdle(): Promise<void>;
104
106
  /** Abort 所有挂起任务 */
105
107
  abort(reason?: string): void;
106
- /** 完整关闭(batch stop + channel close) */
108
+ /** 完整关闭:channel close + pipeline abort + batch stop */
107
109
  close(): void;
108
110
  /** 工具 */
109
111
  uuid(): string;
@@ -119,6 +121,10 @@ export declare class EventTracker {
119
121
  getChannel(): InstanceChannel;
120
122
  getPipeline(): SendPipeline;
121
123
  getSignedIdentity(): SignedIdentity | undefined;
124
+ /** 获取 sender 失败统计快照(v1.2.0) */
125
+ getStats(): import("./stats.js").StatsSnapshot;
126
+ /** 重置 sender 统计 */
127
+ resetStats(): void;
122
128
  isBrowser(): boolean;
123
129
  isInitialized(): boolean;
124
130
  }
@@ -0,0 +1,28 @@
1
+ /**
2
+ * WASM 加密(v1.2.0 可选)
3
+ *
4
+ * - 把常见 HMAC-SHA256 / AES-GCM 操作抽到 wasm(性能 5-10x)
5
+ * - 通过 dynamic import('./crypto-wasm.js') 按需加载
6
+ * - wasm 未提供时 fallback 到 js
7
+ * - 提供 `getWasmCrypto()` lazy 工厂
8
+ *
9
+ * 注意:本目录仅含 runtime glue;实际 wasm binary 由用户在构建期注入
10
+ * (如:npm i @macroui/crypto-wasm 并在 init 时传入)
11
+ */
12
+ export interface WasmCrypto {
13
+ hmacSha256(key: Uint8Array, data: Uint8Array): Uint8Array;
14
+ aesGcmEncrypt(key: Uint8Array, iv: Uint8Array, data: Uint8Array): Uint8Array;
15
+ aesGcmDecrypt(key: Uint8Array, iv: Uint8Array, data: Uint8Array): Uint8Array;
16
+ available: boolean;
17
+ }
18
+ /**
19
+ * 加载 wasm crypto
20
+ * - 优先尝试 globalThis.__ET_WASM_CRYPTO__(用户注入)
21
+ * - 否则尝试 import('@macroui/crypto-wasm') peer dep
22
+ * - 失败时 fallback 到 JS 实现
23
+ */
24
+ export declare function getWasmCrypto(): Promise<WasmCrypto>;
25
+ /** 同步 hash 工具(用于 cache key,fallback) */
26
+ export declare function fastHash(s: string): number;
27
+ /** 注入自定义 wasm crypto(advanced 用) */
28
+ export declare function setWasmCrypto(c: WasmCrypto): void;
@@ -0,0 +1,41 @@
1
+ /**
2
+ * Edge Worker Adapter (v1.3.0)
3
+ *
4
+ * - 适配 Cloudflare Workers / D1
5
+ * - 不依赖 DOM,用 globalThis.fetch / crypto
6
+ * - KV 存储用 Map(运行时)
7
+ * - 暴露 init() 工厂
8
+ */
9
+ import type { TrackerConfig } from '../types/index.js';
10
+ export interface EdgeEnv {
11
+ /** 转发到真实 server_url 的可选 fetcher */
12
+ fetch?: typeof fetch;
13
+ /** D1 binding(可选,用于去重 / 缓冲) */
14
+ DB?: {
15
+ prepare: (sql: string) => {
16
+ bind: (...args: unknown[]) => {
17
+ run: () => Promise<unknown>;
18
+ all: () => Promise<{
19
+ results?: unknown[];
20
+ }>;
21
+ };
22
+ };
23
+ };
24
+ }
25
+ export interface EdgeInitOptions extends Partial<TrackerConfig> {
26
+ /** Cloudflare env */
27
+ env?: EdgeEnv;
28
+ /** 队列缓冲上限 */
29
+ maxQueue?: number;
30
+ /** flush 间隔(ms) */
31
+ flushIntervalMs?: number;
32
+ }
33
+ export interface EdgeTracker {
34
+ track: (event: string, properties?: Record<string, unknown>) => Promise<void>;
35
+ flush: () => Promise<void>;
36
+ size: () => number;
37
+ close: () => void;
38
+ }
39
+ export declare function initEdge(options: EdgeInitOptions): EdgeTracker;
40
+ /** 单事件便捷方法(不缓冲,立即发送) */
41
+ export declare function trackOnce(event: string, properties: Record<string, unknown>, options: EdgeInitOptions): Promise<void>;
@@ -0,0 +1,34 @@
1
+ /**
2
+ * Module Federation 入口 (v1.3.0)
3
+ *
4
+ * - 通过 @macroui/event-tracker/federation 暴露
5
+ * - 暴露 named exports 让 host 应用可选择性加载
6
+ * - 输出格式 ESM
7
+ */
8
+ export * from '../core/tracker.js';
9
+ export { EventTracker, initPara, registerAppid, listInstances } from '../core/tracker.js';
10
+ export { SendPipeline } from '../core/send-pipeline.js';
11
+ export { RetryPolicy } from '../core/retry-policy.js';
12
+ export { FailedQueue } from '../core/failed-queue.js';
13
+ export { StatsCollector, GLOBAL_STATS } from '../core/stats.js';
14
+ export type { StatsSnapshot, SenderStat } from '../core/stats.js';
15
+ export { autoTrack } from '../plugins/auto-track/index.js';
16
+ export { pageLoad } from '../plugins/pageload/index.js';
17
+ export { pageLeave } from '../plugins/pageleave/index.js';
18
+ export { exposure } from '../plugins/exposure/index.js';
19
+ export { sessionEvent } from '../plugins/session-event/index.js';
20
+ export { debugSender } from '../plugins/debug-sender/index.js';
21
+ export { indexedDBSender } from '../plugins/indexeddb-sender/index.js';
22
+ export { webviewBridge } from '../plugins/webview-bridge/index.js';
23
+ export { encryptor, xorEncryptor, aesGcmEncryptAsync } from '../plugins/encrypt/index.js';
24
+ export { otelBridge } from '../plugins/otel-bridge/index.js';
25
+ export { otelExporter } from '../plugins/otel-exporter/index.js';
26
+ export { experiment, createExperiment } from '../plugins/experiment/index.js';
27
+ export { predictiveBatcher } from '../plugins/predictive-batcher/index.js';
28
+ export { piiDetector } from '../plugins/pii-detector/index.js';
29
+ export { privacy } from '../plugins/privacy/index.js';
30
+ export { crossDomainStitching } from '../plugins/cross-domain/index.js';
31
+ export { schemaRegistry } from '../plugins/schema-registry/index.js';
32
+ export { rateLimiter } from '../plugins/rate-limiter/index.js';
33
+ export { cspCompliant } from '../plugins/csp-compliant/index.js';
34
+ export { audienceSync } from '../plugins/audience-sync/index.js';
@@ -13,7 +13,7 @@ export default tracker;
13
13
  export { tracker };
14
14
  export { EventTracker };
15
15
  export { initPara, registerAppid, listInstances } from './core/tracker.js';
16
- export type { TrackerConfig, BaseConfig, SendConfig, StorageConfig, IdentityConfig, EncryptConfig, PresetConfig, DebugConfig, JsAppConfig, ClientConfig, DebugSenderConfig, EventData, SendType, StorageType, Callback, LogLevel, JSONValue, JSONObject, JSONArray, PropertyMap, ServerURL, StageName, HookName, } from './types/index.js';
16
+ export type { TrackerConfig, BaseConfig, SendConfig, StorageConfig, IdentityConfig, EncryptConfig, PresetConfig, DebugConfig, ObservabilityConfig, JsAppConfig, ClientConfig, DebugSenderConfig, EventData, SendType, StorageType, Callback, LogLevel, JSONValue, JSONObject, JSONArray, PropertyMap, ServerURL, StageName, HookName, } from './types/index.js';
17
17
  export type { Plugin, InstallContext } from './core/plugin.js';
18
18
  export type { StageInterceptor, StageContext, StageChain } from './core/stage.js';
19
19
  export type { Lifecycle, HookFn } from './core/lifecycle.js';
@@ -28,6 +28,27 @@ export { InstanceChannel } from './core/instance-channel.js';
28
28
  export { Logger } from './core/logger.js';
29
29
  export { IdentityManager } from './core/identity.js';
30
30
  export { PresetPropertyBuilder } from './presets/preset-properties.js';
31
+ export { StatsCollector, GLOBAL_STATS } from './core/stats.js';
32
+ export type { StatsSnapshot, SenderStat } from './core/stats.js';
33
+ export { detectPlatform, platformStore, isPlatformSenderEnabled } from './core/platform.js';
34
+ export type { Platform } from './core/platform.js';
35
+ export { getWasmCrypto, fastHash, setWasmCrypto } from './core/wasm-crypto.js';
36
+ export type { WasmCrypto } from './core/wasm-crypto.js';
37
+ export { hmacSign, hmacSignSync, hmacVerify, signPayload } from './core/payload-signer.js';
38
+ export type { SignOptions } from './core/payload-signer.js';
39
+ export { PiiDetector, fnv1a, maskValue, DEFAULT_PATTERNS } from './core/pii.js';
40
+ export type { PiiOptions, PiiAction, PiiPattern } from './core/pii.js';
41
+ export { PrivacyManager } from './core/privacy.js';
42
+ export type { PrivacyMode, ConsentScope, PrivacyState } from './core/privacy.js';
43
+ export { createReplay } from './core/replay.js';
44
+ export type { ReplayEvent, ReplayOptions, ReplayHandle } from './core/replay.js';
45
+ export { createIdleScheduler, whenIdle, globalIdleScheduler } from './core/idle.js';
46
+ export type { IdleScheduler, IdleCallback } from './core/idle.js';
47
+ export { OffscreenSender } from './send/offscreen-sender.js';
48
+ export { WebSocketSender } from './send/ws-sender.js';
49
+ export type { WebSocketSenderOptions } from './send/ws-sender.js';
50
+ export { initEdge, trackOnce } from './edge/index.js';
51
+ export type { EdgeTracker, EdgeInitOptions, EdgeEnv } from './edge/index.js';
31
52
  export { PresetEvent, PresetProperty, LIB_NAME, LIB_VERSION };
32
53
  export { autoTrack } from './plugins/auto-track/index.js';
33
54
  export { pageLoad } from './plugins/pageload/index.js';
@@ -37,4 +58,24 @@ export { sessionEvent } from './plugins/session-event/index.js';
37
58
  export { debugSender } from './plugins/debug-sender/index.js';
38
59
  export { indexedDBSender } from './plugins/indexeddb-sender/index.js';
39
60
  export { webviewBridge } from './plugins/webview-bridge/index.js';
61
+ export type { BridgeAPI, WebViewBridgeOptions } from './plugins/webview-bridge/index.js';
40
62
  export { encryptor, xorEncryptor, defaultEncryptor, defaultDecryptor, aesGcmEncryptAsync, aesGcmDecryptAsync } from './plugins/encrypt/index.js';
63
+ export { otelBridge } from './plugins/otel-bridge/index.js';
64
+ export { otelExporter } from './plugins/otel-exporter/index.js';
65
+ export type { OtlpHttpOptions, SpanData, OtelEvent, OtelExporterOptions } from './plugins/otel-exporter/index.js';
66
+ export { experiment, createExperiment } from './plugins/experiment/index.js';
67
+ export type { ExperimentVariant, ExperimentOptions, ExperimentContext } from './plugins/experiment/index.js';
68
+ export { predictiveBatcher, makeIntervalPredictor } from './plugins/predictive-batcher/index.js';
69
+ export { piiDetector } from './plugins/pii-detector/index.js';
70
+ export { privacy } from './plugins/privacy/index.js';
71
+ export type { PrivacyOptions } from './plugins/privacy/index.js';
72
+ export { crossDomainStitching } from './plugins/cross-domain/index.js';
73
+ export type { CrossDomainOptions } from './plugins/cross-domain/index.js';
74
+ export { schemaRegistry, SchemaRegistry } from './plugins/schema-registry/index.js';
75
+ export type { SchemaEntry, SchemaOptions } from './plugins/schema-registry/index.js';
76
+ export { rateLimiter, RateLimiter } from './plugins/rate-limiter/index.js';
77
+ export type { RateLimiterOptions, RateLimitRule } from './plugins/rate-limiter/index.js';
78
+ export { cspCompliant } from './plugins/csp-compliant/index.js';
79
+ export type { CspOptions } from './plugins/csp-compliant/index.js';
80
+ export { audienceSync, AudienceSync } from './plugins/audience-sync/index.js';
81
+ export type { AudienceDestination, AudienceSyncOptions, AudienceContext } from './plugins/audience-sync/index.js';
@@ -0,0 +1,67 @@
1
+ /**
2
+ * Audience Sync(v1.3.0)
3
+ *
4
+ * - 用户登录/属性变更后,把 distinct_id 同步到外部平台(Mailchimp / Braze / 自定义 webhook)
5
+ * - 订阅式:sdk.on('identify', cb)
6
+ * - 支持多 destination
7
+ */
8
+ export interface AudienceDestination {
9
+ name: string;
10
+ endpoint: string;
11
+ method?: 'POST' | 'PUT';
12
+ headers?: Record<string, string>;
13
+ /** 转换器:把 distinctId + props 转成目标平台格式 */
14
+ transform?: (data: {
15
+ distinct_id: string;
16
+ properties: Record<string, unknown>;
17
+ traits?: Record<string, unknown>;
18
+ }) => unknown;
19
+ }
20
+ export interface AudienceSyncOptions {
21
+ destinations: AudienceDestination[];
22
+ /** 触发条件:'identify' | 'login' | 'all' */
23
+ triggerOn?: 'identify' | 'login' | 'all';
24
+ /** 失败重试次数 */
25
+ maxRetry?: number;
26
+ }
27
+ export interface AudienceContext {
28
+ subscribe(fn: (data: {
29
+ distinct_id: string;
30
+ properties?: Record<string, unknown>;
31
+ traits?: Record<string, unknown>;
32
+ trigger: string;
33
+ }) => void): () => void;
34
+ flush(): Promise<void>;
35
+ queueSize(): number;
36
+ }
37
+ export declare class AudienceSync {
38
+ options: AudienceSyncOptions;
39
+ private listeners;
40
+ private pending;
41
+ constructor(options: AudienceSyncOptions);
42
+ subscribe(fn: (data: {
43
+ distinct_id: string;
44
+ properties?: Record<string, unknown>;
45
+ traits?: Record<string, unknown>;
46
+ trigger: string;
47
+ }) => void): () => void;
48
+ emit(data: {
49
+ distinct_id: string;
50
+ properties?: Record<string, unknown>;
51
+ traits?: Record<string, unknown>;
52
+ trigger: string;
53
+ }): void;
54
+ /** 缓存到队列(用于晚点批量) */
55
+ enqueue(data: {
56
+ distinct_id: string;
57
+ properties?: Record<string, unknown>;
58
+ traits?: Record<string, unknown>;
59
+ trigger: string;
60
+ }): void;
61
+ queueSize(): number;
62
+ /** 手动 flush:把队列里的事件推到所有 destination */
63
+ flush(): Promise<void>;
64
+ private send;
65
+ }
66
+ import type { Plugin } from '../../core/plugin.js';
67
+ export declare function audienceSync(options: AudienceSyncOptions): Plugin;
@@ -0,0 +1,20 @@
1
+ /**
2
+ * Cross-domain Stitching(v1.3.0)
3
+ *
4
+ * - 在 cookie 写入 _sa_link_id(同根域跨子域共享)
5
+ * - 客户端初始化时检测:当前 distinct_id 是否与 _sa_link_id 绑定
6
+ * - 未登录用户跨子域跳转时,session 连续
7
+ * - 不依赖登录态
8
+ */
9
+ import type { Plugin } from '../../core/plugin.js';
10
+ export interface CrossDomainOptions {
11
+ /** cookie 名,默认 _sa_link_id */
12
+ cookieName?: string;
13
+ /** 共享域(如 .example.com),自动加 . */
14
+ domain?: string;
15
+ /** 过期天数,默认 365 */
16
+ expiresDays?: number;
17
+ /** 是否把 _sa_link_id 注入到 register / event properties */
18
+ injectProperty?: boolean;
19
+ }
20
+ export declare function crossDomainStitching(opts?: CrossDomainOptions): Plugin;
@@ -0,0 +1,17 @@
1
+ /**
2
+ * CSP Nonce 支持(v1.3.0)
3
+ *
4
+ * - 从 meta[name=csp-nonce] 或 config.csp_nonce 读 nonce
5
+ * - 在 sendDataStage 给所有事件加 $csp_nonce 属性
6
+ * - 业务侧可以用它把数据通过合法 CSP 通道回传到自家 server
7
+ */
8
+ import type { Plugin } from '../../core/plugin.js';
9
+ export interface CspOptions {
10
+ /** 直接传 nonce 字符串 */
11
+ nonce?: string;
12
+ /** 从 meta[name=csp-nonce] 读 */
13
+ metaSelector?: string;
14
+ /** 是否自动注册为 event property */
15
+ injectProperty?: boolean;
16
+ }
17
+ export declare function cspCompliant(opts?: CspOptions): Plugin;
@@ -0,0 +1,43 @@
1
+ /**
2
+ * A/B Test / 实验埋点 helper(v1.2.0)
3
+ *
4
+ * 提供:
5
+ * - sdk.experiment(key, variants): 根据 variants 配置确定分组,sticky(localStorage)
6
+ * - 每次 track 时自动注入 $experiment_key / $variant_id
7
+ * - 支持曝光事件:exposure(key, variant)
8
+ * - 不依赖外部实验平台 SDK
9
+ */
10
+ import type { Plugin } from '../../core/plugin.js';
11
+ import type { StorageType } from '../../types/index.js';
12
+ export interface ExperimentVariant {
13
+ /** 实验分组 id */
14
+ id: string;
15
+ /** 权重(数字,绝对值或 0-100 百分比) */
16
+ weight?: number;
17
+ /** 默认附加的 properties(会 merge 到事件 properties) */
18
+ properties?: Record<string, unknown>;
19
+ }
20
+ export interface ExperimentOptions {
21
+ /** 自定义存储前缀 */
22
+ storagePrefix?: string;
23
+ /** 存储类型(默认 localStorage) */
24
+ storage?: StorageType;
25
+ }
26
+ export interface ExperimentContext {
27
+ /** 拉取指定实验的分组(无配置返回 null) */
28
+ variantOf: (key: string) => ExperimentVariant | null;
29
+ /** 直接获取 variant id */
30
+ variantIdOf: (key: string) => string | null;
31
+ /** 上报曝光(一次会话只上报一次) */
32
+ exposure: (key: string, properties?: Record<string, unknown>) => void;
33
+ /** 强制设置(debug 用) */
34
+ forceSet: (key: string, variantId: string) => void;
35
+ /** 列出当前所有已分配 */
36
+ list: () => Record<string, string>;
37
+ }
38
+ /**
39
+ * 创建实验上下文(不依赖 SDK,可单独用)
40
+ */
41
+ export declare function createExperiment(experiments: Record<string, ExperimentVariant[]>, opts?: ExperimentOptions): ExperimentContext;
42
+ /** 插件形态:把 experiment 注入到事件 properties */
43
+ export declare function experiment(experiments: Record<string, ExperimentVariant[]>, opts?: ExperimentOptions): Plugin;
@@ -0,0 +1,22 @@
1
+ /**
2
+ * OpenTelemetry Bridge Plugin (v1.2.0)
3
+ *
4
+ * 把 SDK 事件转发到 OTel:
5
+ * - track → otel tracer.startActiveSpan
6
+ * - 用 @opentelemetry/api 作为可选 peer dependency
7
+ * - 通过 dynamic import 兼容未安装 OTel 的场景
8
+ * - 属性透传:event 类型 / properties → span attributes
9
+ * - 支持自定义 mapper
10
+ */
11
+ import type { Plugin } from '../../core/plugin.js';
12
+ export interface OtelBridgeOptions {
13
+ /** tracer 名(默认 '@macroui/event-tracker') */
14
+ tracerName?: string;
15
+ /** span 名映射:(eventName) => spanName,默认 = eventName */
16
+ spanName?: (event: string) => string;
17
+ /** 属性过滤:返回 false 的属性不上报 */
18
+ filterAttr?: (key: string, value: unknown) => boolean;
19
+ /** 全局关闭 */
20
+ enabled?: boolean;
21
+ }
22
+ export declare function otelBridge(opts?: OtelBridgeOptions): Plugin;
@@ -0,0 +1,50 @@
1
+ /**
2
+ * OpenTelemetry Exporter (v1.3.0)
3
+ *
4
+ * - OTLP/HTTP + OTLP/gRPC 两种协议
5
+ * - 把 EventTracker 事件 → OTel Span
6
+ * - 不依赖 @opentelemetry/api(内部实现)
7
+ * - 可独立 import:@macroui/event-tracker/plugin/otel-exporter
8
+ */
9
+ export interface OtlpHttpOptions {
10
+ endpoint: string;
11
+ headers?: Record<string, string>;
12
+ /** gzip */
13
+ gzip?: boolean;
14
+ /** timeout (ms) */
15
+ timeoutMs?: number;
16
+ }
17
+ export interface SpanData {
18
+ name: string;
19
+ kind?: 'SPAN_KIND_INTERNAL' | 'SPAN_KIND_CLIENT' | 'SPAN_KIND_SERVER';
20
+ startTimeUnixNano: bigint | number;
21
+ endTimeUnixNano: bigint | number;
22
+ attributes: Array<{
23
+ key: string;
24
+ value: {
25
+ stringValue?: string;
26
+ intValue?: number | bigint;
27
+ boolValue?: boolean;
28
+ };
29
+ }>;
30
+ traceId: string;
31
+ spanId: string;
32
+ }
33
+ export interface OtelEvent {
34
+ name: string;
35
+ properties?: Record<string, unknown>;
36
+ time: number;
37
+ distinctId?: string;
38
+ }
39
+ export declare function eventToSpan(ev: OtelEvent): SpanData;
40
+ export declare function exportOtlpHttp(events: OtelEvent[], opts: OtlpHttpOptions): Promise<void>;
41
+ /** OTel Exporter Plugin 形态 */
42
+ export interface OtelExporterOptions extends OtlpHttpOptions {
43
+ /** 上报前过滤 */
44
+ filter?: (ev: OtelEvent) => boolean;
45
+ /** 批量上报:攒够 N 条 / T ms 触发 */
46
+ batchSize?: number;
47
+ batchIntervalMs?: number;
48
+ }
49
+ import type { Plugin } from '../../core/plugin.js';
50
+ export declare function otelExporter(opts: OtelExporterOptions): Plugin;
@@ -0,0 +1,8 @@
1
+ /**
2
+ * PII Detection Plugin (v1.3.0)
3
+ *
4
+ * 在 sendDataStage 拦截所有事件 properties,扫描 PII 并做脱敏
5
+ */
6
+ import type { Plugin } from '../../core/plugin.js';
7
+ import type { PiiOptions } from '../../core/pii.js';
8
+ export declare function piiDetector(opts?: PiiOptions): Plugin;
@@ -0,0 +1,29 @@
1
+ /**
2
+ * Predictive Batching(v1.2.0)
3
+ *
4
+ * - 监听 user activity(click/scroll/keypress/mousemove 节流)
5
+ * - 高活动期:缩短 batch flush 间隔
6
+ * - 低活动期:拉长间隔,省电 / 省流量
7
+ * - 通过 SDK config.batch_send.dynamic_interval 启用
8
+ *
9
+ * 不属于 SDK 强耦合:作为可选插件
10
+ */
11
+ import type { Plugin } from '../../core/plugin.js';
12
+ export interface PredictiveBatchOptions {
13
+ /** 最小间隔(活动期) */
14
+ minInterval?: number;
15
+ /** 最大间隔(静默期) */
16
+ maxInterval?: number;
17
+ /** 活动统计窗口(ms) */
18
+ windowMs?: number;
19
+ /** 活动阈值(窗口内事件 > 此数视为活动期) */
20
+ activityThreshold?: number;
21
+ /** 是否监听这些事件类型 */
22
+ events?: ('click' | 'scroll' | 'keypress' | 'mousemove' | 'touchstart')[];
23
+ }
24
+ /**
25
+ * 不修改 SDK 内部,而是提供一个工具函数 getInterval(opts)
26
+ * 业务侧在 BatchSender.flush interval 决策时调用
27
+ */
28
+ export declare function makeIntervalPredictor(opts?: PredictiveBatchOptions): () => number;
29
+ export declare function predictiveBatcher(opts?: PredictiveBatchOptions): Plugin;
@@ -0,0 +1,19 @@
1
+ /**
2
+ * Privacy & Consent Plugin (v1.3.0)
3
+ *
4
+ * - 接入 PrivacyManager 到 SDK
5
+ * - sendDataStage 拦截:
6
+ * 1. 未授权 scope → drop
7
+ * 2. 按 privacy_mode 脱敏
8
+ * - 在 sdk 上挂 sdk.privacy / sdk.consent API
9
+ */
10
+ import type { Plugin } from '../../core/plugin.js';
11
+ import type { ConsentScope, PrivacyMode } from '../../core/privacy.js';
12
+ export interface PrivacyOptions {
13
+ mode?: PrivacyMode;
14
+ /** 缺哪些 scope 时不 track?默认 ['analytics'] */
15
+ requireScopes?: ConsentScope[];
16
+ /** 是否在 init 时打印授权 banner */
17
+ showBanner?: boolean;
18
+ }
19
+ export declare function privacy(opts?: PrivacyOptions): Plugin;
@@ -0,0 +1,41 @@
1
+ /**
2
+ * Rate Limiter(v1.3.0)
3
+ *
4
+ * - 三档限流:
5
+ * 1. 全局(global):每秒最多 N 条
6
+ * 2. 用户级(user):每用户每秒最多 M 条
7
+ * 3. per-event(event):每个事件名每秒最多 K 条
8
+ * - 超出 drop + 触发 onDrop 回调
9
+ * - 用滑动窗口(100ms bucket)实现
10
+ */
11
+ export interface RateLimitRule {
12
+ /** 时间窗口(ms) */
13
+ windowMs: number;
14
+ /** 窗口内最大条数 */
15
+ max: number;
16
+ }
17
+ export interface RateLimiterOptions {
18
+ global?: RateLimitRule;
19
+ user?: RateLimitRule;
20
+ perEvent?: RateLimitRule;
21
+ /** 触发 drop 回调 */
22
+ onDrop?: (info: {
23
+ scope: 'global' | 'user' | 'event';
24
+ key?: string;
25
+ event?: string;
26
+ }) => void;
27
+ }
28
+ export declare class RateLimiter {
29
+ private opts;
30
+ private globalBuckets;
31
+ private userBuckets;
32
+ private eventBuckets;
33
+ constructor(opts: RateLimiterOptions);
34
+ /** 是否允许 */
35
+ allow(event: string, userId?: string): boolean;
36
+ private checkBucket;
37
+ /** 清空所有 bucket */
38
+ reset(): void;
39
+ }
40
+ import type { Plugin } from '../../core/plugin.js';
41
+ export declare function rateLimiter(opts: RateLimiterOptions): Plugin;
@@ -0,0 +1,41 @@
1
+ /**
2
+ * Schema Registry 校验(v1.3.0)
3
+ *
4
+ * - 内置默认 schemas:pageview / track / profile_set
5
+ * - 支持自定义 schemas:schema({eventName, jsonSchema})
6
+ * - 远程 schema URL:服务端可下发(带 ETag 缓存)
7
+ * - 校验失败:默认 warn + 仍上报(可配置 drop)
8
+ * - 动态 import ajv,未安装时 noop
9
+ */
10
+ import type { Plugin } from '../../core/plugin.js';
11
+ export interface SchemaEntry {
12
+ /** 事件名 */
13
+ event: string;
14
+ /** JSON Schema(Draft-07 兼容) */
15
+ schema: Record<string, unknown>;
16
+ }
17
+ export interface SchemaOptions {
18
+ /** 自定义 schemas */
19
+ schemas?: SchemaEntry[];
20
+ /** 远程 schema URL(HTTP 拉取,带 ETag) */
21
+ remoteUrl?: string;
22
+ /** 校验失败处理 */
23
+ onInvalid?: 'warn' | 'drop' | 'pass';
24
+ /** 远程 schema TTL(ms),默认 1h */
25
+ remoteTtlMs?: number;
26
+ }
27
+ export declare class SchemaRegistry {
28
+ private opts;
29
+ private ajv;
30
+ private entries;
31
+ private remoteCache;
32
+ constructor(opts: SchemaOptions);
33
+ init(): Promise<void>;
34
+ add(entry: SchemaEntry): void;
35
+ private fetchRemote;
36
+ validate(event: string, data: unknown): {
37
+ ok: boolean;
38
+ errors?: unknown[];
39
+ };
40
+ }
41
+ export declare function schemaRegistry(opts?: SchemaOptions): Plugin;