@wxt-dev/analytics 0.4.0 → 0.5.0

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 CHANGED
@@ -172,3 +172,98 @@ export default defineAppConfig({
172
172
  ```
173
173
 
174
174
  Example `AnalyticsProvider` implementations can be found at [`./modules/analytics/providers`](https://github.com/wxt-dev/wxt/tree/main/packages/analytics/modules/analytics/providers).
175
+
176
+ ## User Properties
177
+
178
+ User ID and properties are stored in `browser.storage.local`. To change this or customize where these values are stored, use the `userId` and `userProperties` config:
179
+
180
+ ```ts
181
+ // app.config.ts
182
+ import { storage } from 'wxt/storage';
183
+
184
+ export default defineAppConfig({
185
+ analytics: {
186
+ userId: storage.defineItem('local:custom-user-id-key'),
187
+ userProperties: storage.defineItem('local:custom-user-properties-key'),
188
+ },
189
+ });
190
+ ```
191
+
192
+ To set the values at runtime, use the `identify` function:
193
+
194
+ ```ts
195
+ await analytics.identify(userId, userProperties);
196
+ ```
197
+
198
+ Alternatively, a common pattern is to use a random string as the user ID. This keeps the actual user information private, while still providing useful metrics in your analytics platform. This can be done very easily using WXT's storage API:
199
+
200
+ ```ts
201
+ // app.config.ts
202
+ import { storage } from 'wxt/storage';
203
+
204
+ export default defineAppConfig({
205
+ analytics: {
206
+ userId: storage.defineItem('local:custom-user-id-key', {
207
+ init: () => crypto.randomUUID(),
208
+ }),
209
+ },
210
+ });
211
+ ```
212
+
213
+ If you aren't using `wxt` or `@wxt-dev/storage`, you can define custom implementations for the `userId` and `userProperties` config:
214
+
215
+ ```ts
216
+ const analytics = createAnalytics({
217
+ userId: {
218
+ getValue: () => ...,
219
+ setValue: (userId) => ...,
220
+ }
221
+ })
222
+ ```
223
+
224
+ ## Auto-track UI events
225
+
226
+ Call `analytics.autoTrack(container)` to automatically track UI events so you don't have to manually add them. Currently it:
227
+
228
+ - Tracks clicks to elements inside the `container`
229
+
230
+ In your extension's HTML pages, you'll want to call it with `document`:
231
+
232
+ ```ts
233
+ analytics.autoTrack(document);
234
+ ```
235
+
236
+ But in content scripts, you usually only care about interactions with your own UI:
237
+
238
+ ```ts
239
+ const ui = createIntegratedUi({
240
+ // ...
241
+ onMount(container) {
242
+ analytics.autoTrack(container);
243
+ },
244
+ });
245
+ ui.mount();
246
+ ```
247
+
248
+ ## Enabling/Disabling
249
+
250
+ By default, **analytics is disabled**. You can configure how the value is stored (and change the default value) via the `enabled` config:
251
+
252
+ ```ts
253
+ // app.config.ts
254
+ import { storage } from 'wxt/storage';
255
+
256
+ export default defineAppConfig({
257
+ analytics: {
258
+ enabled: storage.defineItem('local:analytics-enabled', {
259
+ fallback: true,
260
+ }),
261
+ },
262
+ });
263
+ ```
264
+
265
+ At runtime, you can call `setEnabled` to change the value:
266
+
267
+ ```ts
268
+ analytics.setEnabled(true);
269
+ ```
package/dist/index.mjs CHANGED
@@ -68,8 +68,7 @@ function createBackgroundAnalytics(config) {
68
68
  userPropertiesStorage.setValue?.(newUserProperties)
69
69
  ]);
70
70
  const event = await getBaseEvent(meta);
71
- if (config?.debug)
72
- console.debug("[@wxt-dev/analytics] identify", event);
71
+ if (config?.debug) console.debug("[@wxt-dev/analytics] identify", event);
73
72
  if (await enabled.getValue()) {
74
73
  await Promise.allSettled(
75
74
  providers.map((provider) => provider.identify(event))
@@ -90,8 +89,7 @@ function createBackgroundAnalytics(config) {
90
89
  title: meta?.title ?? globalThis.document?.title
91
90
  }
92
91
  };
93
- if (config?.debug)
94
- console.debug("[@wxt-dev/analytics] page", event);
92
+ if (config?.debug) console.debug("[@wxt-dev/analytics] page", event);
95
93
  if (await enabled.getValue()) {
96
94
  await Promise.allSettled(
97
95
  providers.map((provider) => provider.page(event))
@@ -108,8 +106,7 @@ function createBackgroundAnalytics(config) {
108
106
  ...baseEvent,
109
107
  event: { name: eventName, properties: eventProperties }
110
108
  };
111
- if (config?.debug)
112
- console.debug("[@wxt-dev/analytics] track", event);
109
+ if (config?.debug) console.debug("[@wxt-dev/analytics] track", event);
113
110
  if (await enabled.getValue()) {
114
111
  await Promise.allSettled(
115
112
  providers.map((provider) => provider.track(event))
package/dist/module.d.mts CHANGED
@@ -1,7 +1,7 @@
1
1
  import * as wxt from 'wxt';
2
2
  import { AnalyticsConfig } from './types.mjs';
3
3
 
4
- declare module 'wxt/sandbox' {
4
+ declare module 'wxt/utils/define-app-config' {
5
5
  interface WxtAppConfig {
6
6
  analytics: AnalyticsConfig;
7
7
  }
package/dist/module.d.ts CHANGED
@@ -1,7 +1,7 @@
1
1
  import * as wxt from 'wxt';
2
2
  import { AnalyticsConfig } from './types.js';
3
3
 
4
- declare module 'wxt/sandbox' {
4
+ declare module 'wxt/utils/define-app-config' {
5
5
  interface WxtAppConfig {
6
6
  analytics: AnalyticsConfig;
7
7
  }
package/dist/module.mjs CHANGED
@@ -1,6 +1,6 @@
1
1
  import 'wxt';
2
- import 'wxt/sandbox';
3
- import { defineWxtModule, addAlias, addWxtPlugin } from 'wxt/modules';
2
+ import 'wxt/utils/define-app-config';
3
+ import { defineWxtModule, addAlias, addWxtPlugin, addViteConfig } from 'wxt/modules';
4
4
  import { resolve } from 'node:path';
5
5
 
6
6
  const index = defineWxtModule({
@@ -12,14 +12,14 @@ const index = defineWxtModule({
12
12
  const clientModuleId = "@wxt-dev/analytics" ;
13
13
  const pluginModuleId = "@wxt-dev/analytics/background-plugin" ;
14
14
  wxt.hook("build:manifestGenerated", (_, manifest) => {
15
- manifest.permissions ?? (manifest.permissions = []);
15
+ manifest.permissions ??= [];
16
16
  if (!manifest.permissions.includes("storage")) {
17
17
  manifest.permissions.push("storage");
18
18
  }
19
19
  });
20
20
  const wxtAnalyticsCode = [
21
21
  `import { createAnalytics } from '${clientModuleId }';`,
22
- `import { useAppConfig } from 'wxt/client';`,
22
+ `import { useAppConfig } from '#imports';`,
23
23
  ``,
24
24
  `export const analytics = createAnalytics(useAppConfig().analytics);`,
25
25
  ``
@@ -47,6 +47,14 @@ const index = defineWxtModule({
47
47
  }
48
48
  });
49
49
  addWxtPlugin(wxt, pluginModuleId);
50
+ addViteConfig(wxt, () => ({
51
+ optimizeDeps: {
52
+ // Ensure the "#analytics" import is processed by vite in the background plugin
53
+ exclude: ["@wxt-dev/analytics"],
54
+ // Ensure the CJS subdependency is preprocessed into ESM
55
+ include: ["@wxt-dev/analytics > ua-parser-js"]
56
+ }
57
+ }));
50
58
  }
51
59
  });
52
60
 
package/dist/types.d.mts CHANGED
@@ -1,13 +1,13 @@
1
1
  interface Analytics {
2
- /** Report a page change */
2
+ /** Report a page change. */
3
3
  page: (url: string) => void;
4
- /** Report a custom event */
4
+ /** Report a custom event. */
5
5
  track: (eventName: string, eventProperties?: Record<string, string>) => void;
6
- /** Save information about the user */
6
+ /** Save information about the user. */
7
7
  identify: (userId: string, userProperties?: Record<string, string>) => void;
8
8
  /** Automatically setup and track user interactions, returning a function to remove any listeners that were setup. */
9
9
  autoTrack: (root: Document | ShadowRoot | Element) => () => void;
10
- /** Calls `config.enabled.setValue` */
10
+ /** Calls `config.enabled.setValue`. */
11
11
  setEnabled: (enabled: boolean) => void;
12
12
  }
13
13
  interface AnalyticsConfig {
@@ -20,19 +20,20 @@ interface AnalyticsConfig {
20
20
  */
21
21
  debug?: boolean;
22
22
  /**
23
- * Extension version, defaults to `browser.runtime.getManifest().version`.
23
+ * Your extension's version, reported alongside events.
24
+ * @default browser.runtime.getManifest().version`.
24
25
  */
25
26
  version?: string;
26
27
  /**
27
- * Configure how the enabled flag is persisted. Defaults to using `""` in local extension storage.
28
+ * Configure how the enabled flag is persisted. Defaults to using `browser.storage.local`.
28
29
  */
29
30
  enabled?: AnalyticsStorageItem<boolean>;
30
31
  /**
31
- * Configure how the user Id is persisted
32
+ * Configure how the user Id is persisted. Defaults to using `browser.storage.local`.
32
33
  */
33
34
  userId?: AnalyticsStorageItem<string>;
34
35
  /**
35
- * Configure how user properties are persisted
36
+ * Configure how user properties are persisted. Defaults to using `browser.storage.local`.
36
37
  */
37
38
  userProperties?: AnalyticsStorageItem<Record<string, string>>;
38
39
  }
@@ -41,11 +42,11 @@ interface AnalyticsStorageItem<T> {
41
42
  setValue?: (newValue: T) => void | Promise<void>;
42
43
  }
43
44
  type AnalyticsProvider = (analytics: Analytics, config: AnalyticsConfig) => {
44
- /** Upload a page view event */
45
+ /** Upload a page view event. */
45
46
  page: (event: AnalyticsPageViewEvent) => Promise<void>;
46
- /** Upload a custom event */
47
+ /** Upload a custom event. */
47
48
  track: (event: AnalyticsTrackEvent) => Promise<void>;
48
- /** Upload information about the user */
49
+ /** Upload information about the user. */
49
50
  identify: (event: BaseAnalyticsEvent) => Promise<void>;
50
51
  };
51
52
  interface BaseAnalyticsEvent {
@@ -56,11 +57,11 @@ interface BaseAnalyticsEvent {
56
57
  };
57
58
  }
58
59
  interface AnalyticsEventMetadata {
59
- /** Identifier of the session the event was fired from */
60
+ /** Identifier of the session the event was fired from. */
60
61
  sessionId: number | undefined;
61
- /** `Date.now()` of when the event was reported */
62
+ /** `Date.now()` of when the event was reported. */
62
63
  timestamp: number;
63
- /** `"1920x1080"` */
64
+ /** Ex: `"1920x1080"`. */
64
65
  screen: string | undefined;
65
66
  /** `document.referrer` */
66
67
  referrer: string | undefined;
package/dist/types.d.ts CHANGED
@@ -1,13 +1,13 @@
1
1
  interface Analytics {
2
- /** Report a page change */
2
+ /** Report a page change. */
3
3
  page: (url: string) => void;
4
- /** Report a custom event */
4
+ /** Report a custom event. */
5
5
  track: (eventName: string, eventProperties?: Record<string, string>) => void;
6
- /** Save information about the user */
6
+ /** Save information about the user. */
7
7
  identify: (userId: string, userProperties?: Record<string, string>) => void;
8
8
  /** Automatically setup and track user interactions, returning a function to remove any listeners that were setup. */
9
9
  autoTrack: (root: Document | ShadowRoot | Element) => () => void;
10
- /** Calls `config.enabled.setValue` */
10
+ /** Calls `config.enabled.setValue`. */
11
11
  setEnabled: (enabled: boolean) => void;
12
12
  }
13
13
  interface AnalyticsConfig {
@@ -20,19 +20,20 @@ interface AnalyticsConfig {
20
20
  */
21
21
  debug?: boolean;
22
22
  /**
23
- * Extension version, defaults to `browser.runtime.getManifest().version`.
23
+ * Your extension's version, reported alongside events.
24
+ * @default browser.runtime.getManifest().version`.
24
25
  */
25
26
  version?: string;
26
27
  /**
27
- * Configure how the enabled flag is persisted. Defaults to using `""` in local extension storage.
28
+ * Configure how the enabled flag is persisted. Defaults to using `browser.storage.local`.
28
29
  */
29
30
  enabled?: AnalyticsStorageItem<boolean>;
30
31
  /**
31
- * Configure how the user Id is persisted
32
+ * Configure how the user Id is persisted. Defaults to using `browser.storage.local`.
32
33
  */
33
34
  userId?: AnalyticsStorageItem<string>;
34
35
  /**
35
- * Configure how user properties are persisted
36
+ * Configure how user properties are persisted. Defaults to using `browser.storage.local`.
36
37
  */
37
38
  userProperties?: AnalyticsStorageItem<Record<string, string>>;
38
39
  }
@@ -41,11 +42,11 @@ interface AnalyticsStorageItem<T> {
41
42
  setValue?: (newValue: T) => void | Promise<void>;
42
43
  }
43
44
  type AnalyticsProvider = (analytics: Analytics, config: AnalyticsConfig) => {
44
- /** Upload a page view event */
45
+ /** Upload a page view event. */
45
46
  page: (event: AnalyticsPageViewEvent) => Promise<void>;
46
- /** Upload a custom event */
47
+ /** Upload a custom event. */
47
48
  track: (event: AnalyticsTrackEvent) => Promise<void>;
48
- /** Upload information about the user */
49
+ /** Upload information about the user. */
49
50
  identify: (event: BaseAnalyticsEvent) => Promise<void>;
50
51
  };
51
52
  interface BaseAnalyticsEvent {
@@ -56,11 +57,11 @@ interface BaseAnalyticsEvent {
56
57
  };
57
58
  }
58
59
  interface AnalyticsEventMetadata {
59
- /** Identifier of the session the event was fired from */
60
+ /** Identifier of the session the event was fired from. */
60
61
  sessionId: number | undefined;
61
- /** `Date.now()` of when the event was reported */
62
+ /** `Date.now()` of when the event was reported. */
62
63
  timestamp: number;
63
- /** `"1920x1080"` */
64
+ /** Ex: `"1920x1080"`. */
64
65
  screen: string | undefined;
65
66
  /** `document.referrer` */
66
67
  referrer: string | undefined;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@wxt-dev/analytics",
3
- "version": "0.4.0",
3
+ "version": "0.5.0",
4
4
  "description": "Add analytics to your web extension",
5
5
  "repository": {
6
6
  "type": "git",
@@ -40,19 +40,19 @@
40
40
  "dist"
41
41
  ],
42
42
  "peerDependencies": {
43
- "wxt": ">=0.19.23"
43
+ "wxt": ">=0.20.0"
44
44
  },
45
45
  "devDependencies": {
46
46
  "@aklinker1/check": "^1.4.5",
47
- "@types/chrome": "^0.0.268",
47
+ "@types/chrome": "^0.0.280",
48
48
  "@types/ua-parser-js": "^0.7.39",
49
49
  "publint": "^0.2.12",
50
50
  "typescript": "^5.6.3",
51
- "unbuild": "^2.0.0",
52
- "wxt": "0.19.23"
51
+ "unbuild": "^3.5.0",
52
+ "wxt": "0.20.0"
53
53
  },
54
54
  "dependencies": {
55
- "ua-parser-js": "^1.0.38"
55
+ "ua-parser-js": "^1.0.40"
56
56
  },
57
57
  "scripts": {
58
58
  "dev": "buildc --deps-only -- wxt",