@better-auth/telemetry 1.3.28

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.
@@ -0,0 +1,13 @@
1
+
2
+ > @better-auth/telemetry@1.3.28 build /home/runner/work/better-auth/better-auth/packages/telemetry
3
+ > unbuild --clean
4
+
5
+ [info] Building telemetry
6
+ [info] Cleaning dist directory: `./dist`
7
+ [success] Build succeeded for telemetry
8
+ [log] dist/index.cjs (total size: 19.3 kB, chunk size: 19.3 kB, exports: createTelemetry, getTelemetryAuthConfig)
9
+
10
+ [log] dist/index.mjs (total size: 19.2 kB, chunk size: 19.2 kB, exports: createTelemetry, getTelemetryAuthConfig)
11
+
12
+ Σ Total dist size (byte size): 58.5 kB
13
+ [log]
package/LICENSE.md ADDED
@@ -0,0 +1,17 @@
1
+ The MIT License (MIT)
2
+ Copyright (c) 2024 - present, Bereket Engida
3
+
4
+ Permission is hereby granted, free of charge, to any person obtaining a copy of this software
5
+ and associated documentation files (the "Software"), to deal in the Software without restriction,
6
+ including without limitation the rights to use, copy, modify, merge, publish, distribute,
7
+ sublicense, and/or sell copies of the Software, and to permit persons to whom the Software
8
+ is furnished to do so, subject to the following conditions:
9
+
10
+ The above copyright notice and this permission notice shall be included in all copies or
11
+ substantial portions of the Software.
12
+
13
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
14
+ BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
15
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
16
+ DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
17
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
@@ -0,0 +1,10 @@
1
+ import { defineBuildConfig } from "unbuild";
2
+
3
+ export default defineBuildConfig({
4
+ entries: ["src/index"],
5
+ declaration: true,
6
+ clean: true,
7
+ rollup: {
8
+ emitCJS: true,
9
+ },
10
+ });
package/dist/index.cjs ADDED
@@ -0,0 +1,564 @@
1
+ 'use strict';
2
+
3
+ const env = require('@better-auth/core/env');
4
+ const random = require('@better-auth/utils/random');
5
+ const hash = require('@better-auth/utils/hash');
6
+ const base64 = require('@better-auth/utils/base64');
7
+ const fetch = require('@better-fetch/fetch');
8
+
9
+ const generateId = (size) => {
10
+ return random.createRandomStringGenerator("a-z", "A-Z", "0-9")(size);
11
+ };
12
+
13
+ async function hashToBase64(data) {
14
+ const buffer = await hash.createHash("SHA-256").digest(data);
15
+ return base64.base64.encode(buffer);
16
+ }
17
+
18
+ let packageJSONCache;
19
+ async function readRootPackageJson() {
20
+ if (packageJSONCache) return packageJSONCache;
21
+ try {
22
+ const cwd = typeof process !== "undefined" && typeof process.cwd === "function" ? process.cwd() : "";
23
+ if (!cwd) return void 0;
24
+ const importRuntime = (m) => Function("mm", "return import(mm)")(m);
25
+ const [{ default: fs }, { default: path }] = await Promise.all([
26
+ importRuntime("fs/promises"),
27
+ importRuntime("path")
28
+ ]);
29
+ const raw = await fs.readFile(path.join(cwd, "package.json"), "utf-8");
30
+ packageJSONCache = JSON.parse(raw);
31
+ return packageJSONCache;
32
+ } catch {
33
+ }
34
+ return void 0;
35
+ }
36
+ async function getPackageVersion(pkg) {
37
+ if (packageJSONCache) {
38
+ return packageJSONCache.dependencies?.[pkg] || packageJSONCache.devDependencies?.[pkg] || packageJSONCache.peerDependencies?.[pkg];
39
+ }
40
+ try {
41
+ const cwd = typeof process !== "undefined" && typeof process.cwd === "function" ? process.cwd() : "";
42
+ if (!cwd) throw new Error("no-cwd");
43
+ const importRuntime = (m) => Function("mm", "return import(mm)")(m);
44
+ const [{ default: fs }, { default: path }] = await Promise.all([
45
+ importRuntime("fs/promises"),
46
+ importRuntime("path")
47
+ ]);
48
+ const pkgJsonPath = path.join(cwd, "node_modules", pkg, "package.json");
49
+ const raw = await fs.readFile(pkgJsonPath, "utf-8");
50
+ const json = JSON.parse(raw);
51
+ const resolved = json.version || await getVersionFromLocalPackageJson(pkg) || void 0;
52
+ return resolved;
53
+ } catch {
54
+ }
55
+ const fromRoot = await getVersionFromLocalPackageJson(pkg);
56
+ return fromRoot;
57
+ }
58
+ async function getVersionFromLocalPackageJson(pkg) {
59
+ const json = await readRootPackageJson();
60
+ if (!json) return void 0;
61
+ const allDeps = {
62
+ ...json.dependencies,
63
+ ...json.devDependencies,
64
+ ...json.peerDependencies
65
+ };
66
+ return allDeps[pkg];
67
+ }
68
+ async function getNameFromLocalPackageJson() {
69
+ const json = await readRootPackageJson();
70
+ return json?.name;
71
+ }
72
+
73
+ let projectIdCached = null;
74
+ async function getProjectId(baseUrl) {
75
+ if (projectIdCached) return projectIdCached;
76
+ const projectName = await getNameFromLocalPackageJson();
77
+ if (projectName) {
78
+ projectIdCached = await hashToBase64(
79
+ baseUrl ? baseUrl + projectName : projectName
80
+ );
81
+ return projectIdCached;
82
+ }
83
+ if (baseUrl) {
84
+ projectIdCached = await hashToBase64(baseUrl);
85
+ return projectIdCached;
86
+ }
87
+ projectIdCached = generateId(32);
88
+ return projectIdCached;
89
+ }
90
+
91
+ const importRuntime = (m) => {
92
+ return Function("mm", "return import(mm)")(m);
93
+ };
94
+
95
+ function getVendor() {
96
+ const hasAny = (...keys) => keys.some((k) => Boolean(env.env[k]));
97
+ if (hasAny("CF_PAGES", "CF_PAGES_URL", "CF_ACCOUNT_ID") || typeof navigator !== "undefined" && navigator.userAgent === "Cloudflare-Workers") {
98
+ return "cloudflare";
99
+ }
100
+ if (hasAny("VERCEL", "VERCEL_URL", "VERCEL_ENV")) return "vercel";
101
+ if (hasAny("NETLIFY", "NETLIFY_URL")) return "netlify";
102
+ if (hasAny(
103
+ "RENDER",
104
+ "RENDER_URL",
105
+ "RENDER_INTERNAL_HOSTNAME",
106
+ "RENDER_SERVICE_ID"
107
+ )) {
108
+ return "render";
109
+ }
110
+ if (hasAny("AWS_LAMBDA_FUNCTION_NAME", "AWS_EXECUTION_ENV", "LAMBDA_TASK_ROOT")) {
111
+ return "aws";
112
+ }
113
+ if (hasAny(
114
+ "GOOGLE_CLOUD_FUNCTION_NAME",
115
+ "GOOGLE_CLOUD_PROJECT",
116
+ "GCP_PROJECT",
117
+ "K_SERVICE"
118
+ )) {
119
+ return "gcp";
120
+ }
121
+ if (hasAny(
122
+ "AZURE_FUNCTION_NAME",
123
+ "FUNCTIONS_WORKER_RUNTIME",
124
+ "WEBSITE_INSTANCE_ID",
125
+ "WEBSITE_SITE_NAME"
126
+ )) {
127
+ return "azure";
128
+ }
129
+ if (hasAny("DENO_DEPLOYMENT_ID", "DENO_REGION")) return "deno-deploy";
130
+ if (hasAny("FLY_APP_NAME", "FLY_REGION", "FLY_ALLOC_ID")) return "fly-io";
131
+ if (hasAny("RAILWAY_STATIC_URL", "RAILWAY_ENVIRONMENT_NAME"))
132
+ return "railway";
133
+ if (hasAny("DYNO", "HEROKU_APP_NAME")) return "heroku";
134
+ if (hasAny("DO_DEPLOYMENT_ID", "DO_APP_NAME", "DIGITALOCEAN"))
135
+ return "digitalocean";
136
+ if (hasAny("KOYEB", "KOYEB_DEPLOYMENT_ID", "KOYEB_APP_NAME")) return "koyeb";
137
+ return null;
138
+ }
139
+ async function detectSystemInfo() {
140
+ try {
141
+ if (getVendor() === "cloudflare") return "cloudflare";
142
+ const os = await importRuntime("os");
143
+ const cpus = os.cpus();
144
+ return {
145
+ deploymentVendor: getVendor(),
146
+ systemPlatform: os.platform(),
147
+ systemRelease: os.release(),
148
+ systemArchitecture: os.arch(),
149
+ cpuCount: cpus.length,
150
+ cpuModel: cpus.length ? cpus[0].model : null,
151
+ cpuSpeed: cpus.length ? cpus[0].speed : null,
152
+ memory: os.totalmem(),
153
+ isWSL: await isWsl(),
154
+ isDocker: await isDocker(),
155
+ isTTY: typeof process !== "undefined" && process.stdout ? process.stdout.isTTY : null
156
+ };
157
+ } catch (e) {
158
+ return {
159
+ systemPlatform: null,
160
+ systemRelease: null,
161
+ systemArchitecture: null,
162
+ cpuCount: null,
163
+ cpuModel: null,
164
+ cpuSpeed: null,
165
+ memory: null,
166
+ isWSL: null,
167
+ isDocker: null,
168
+ isTTY: null
169
+ };
170
+ }
171
+ }
172
+ let isDockerCached;
173
+ async function hasDockerEnv() {
174
+ if (getVendor() === "cloudflare") return false;
175
+ try {
176
+ const fs = await importRuntime("fs");
177
+ fs.statSync("/.dockerenv");
178
+ return true;
179
+ } catch {
180
+ return false;
181
+ }
182
+ }
183
+ async function hasDockerCGroup() {
184
+ if (getVendor() === "cloudflare") return false;
185
+ try {
186
+ const fs = await importRuntime("fs");
187
+ return fs.readFileSync("/proc/self/cgroup", "utf8").includes("docker");
188
+ } catch {
189
+ return false;
190
+ }
191
+ }
192
+ async function isDocker() {
193
+ if (getVendor() === "cloudflare") return false;
194
+ if (isDockerCached === void 0) {
195
+ isDockerCached = await hasDockerEnv() || await hasDockerCGroup();
196
+ }
197
+ return isDockerCached;
198
+ }
199
+ async function isWsl() {
200
+ try {
201
+ if (getVendor() === "cloudflare") return false;
202
+ if (typeof process === "undefined" || process?.platform !== "linux") {
203
+ return false;
204
+ }
205
+ const fs = await importRuntime("fs");
206
+ const os = await importRuntime("os");
207
+ if (os.release().toLowerCase().includes("microsoft")) {
208
+ if (await isInsideContainer()) {
209
+ return false;
210
+ }
211
+ return true;
212
+ }
213
+ return fs.readFileSync("/proc/version", "utf8").toLowerCase().includes("microsoft") ? !await isInsideContainer() : false;
214
+ } catch {
215
+ return false;
216
+ }
217
+ }
218
+ let isInsideContainerCached;
219
+ const hasContainerEnv = async () => {
220
+ if (getVendor() === "cloudflare") return false;
221
+ try {
222
+ const fs = await importRuntime("fs");
223
+ fs.statSync("/run/.containerenv");
224
+ return true;
225
+ } catch {
226
+ return false;
227
+ }
228
+ };
229
+ async function isInsideContainer() {
230
+ if (isInsideContainerCached === void 0) {
231
+ isInsideContainerCached = await hasContainerEnv() || await isDocker();
232
+ }
233
+ return isInsideContainerCached;
234
+ }
235
+ function isCI() {
236
+ return env.env.CI !== "false" && ("BUILD_ID" in env.env || // Jenkins, Cloudbees
237
+ "BUILD_NUMBER" in env.env || // Jenkins, TeamCity (fixed typo: extra space removed)
238
+ "CI" in env.env || // Travis CI, CircleCI, Cirrus CI, Gitlab CI, Appveyor, CodeShip, dsari, Cloudflare
239
+ "CI_APP_ID" in env.env || // Appflow
240
+ "CI_BUILD_ID" in env.env || // Appflow
241
+ "CI_BUILD_NUMBER" in env.env || // Appflow
242
+ "CI_NAME" in env.env || // Codeship and others
243
+ "CONTINUOUS_INTEGRATION" in env.env || // Travis CI, Cirrus CI
244
+ "RUN_ID" in env.env);
245
+ }
246
+
247
+ function detectRuntime() {
248
+ if (typeof Deno !== "undefined") {
249
+ const denoVersion = Deno?.version?.deno ?? null;
250
+ return { name: "deno", version: denoVersion };
251
+ }
252
+ if (typeof Bun !== "undefined") {
253
+ const bunVersion = Bun?.version ?? null;
254
+ return { name: "bun", version: bunVersion };
255
+ }
256
+ if (typeof process !== "undefined" && process?.versions?.node) {
257
+ return { name: "node", version: process.versions.node ?? null };
258
+ }
259
+ return { name: "edge", version: null };
260
+ }
261
+ function detectEnvironment() {
262
+ return env.getEnvVar("NODE_ENV") === "production" ? "production" : isCI() ? "ci" : env.isTest() ? "test" : "development";
263
+ }
264
+
265
+ const DATABASES = {
266
+ pg: "postgresql",
267
+ mysql: "mysql",
268
+ mariadb: "mariadb",
269
+ sqlite3: "sqlite",
270
+ "better-sqlite3": "sqlite",
271
+ "@prisma/client": "prisma",
272
+ mongoose: "mongodb",
273
+ mongodb: "mongodb",
274
+ "drizzle-orm": "drizzle"
275
+ };
276
+ async function detectDatabase() {
277
+ for (const [pkg, name] of Object.entries(DATABASES)) {
278
+ const version = await getPackageVersion(pkg);
279
+ if (version) return { name, version };
280
+ }
281
+ return void 0;
282
+ }
283
+
284
+ const FRAMEWORKS = {
285
+ next: "next",
286
+ nuxt: "nuxt",
287
+ "@remix-run/server-runtime": "remix",
288
+ astro: "astro",
289
+ "@sveltejs/kit": "sveltekit",
290
+ "solid-start": "solid-start",
291
+ "tanstack-start": "tanstack-start",
292
+ hono: "hono",
293
+ express: "express",
294
+ elysia: "elysia",
295
+ expo: "expo"
296
+ };
297
+ async function detectFramework() {
298
+ for (const [pkg, name] of Object.entries(FRAMEWORKS)) {
299
+ const version = await getPackageVersion(pkg);
300
+ if (version) return { name, version };
301
+ }
302
+ return void 0;
303
+ }
304
+
305
+ function detectPackageManager() {
306
+ const userAgent = env.env.npm_config_user_agent;
307
+ if (!userAgent) {
308
+ return void 0;
309
+ }
310
+ const pmSpec = userAgent.split(" ")[0];
311
+ const separatorPos = pmSpec.lastIndexOf("/");
312
+ const name = pmSpec.substring(0, separatorPos);
313
+ return {
314
+ name: name === "npminstall" ? "cnpm" : name,
315
+ version: pmSpec.substring(separatorPos + 1)
316
+ };
317
+ }
318
+
319
+ function getTelemetryAuthConfig(options, context) {
320
+ return {
321
+ database: context?.database,
322
+ adapter: context?.adapter,
323
+ emailVerification: {
324
+ sendVerificationEmail: !!options.emailVerification?.sendVerificationEmail,
325
+ sendOnSignUp: !!options.emailVerification?.sendOnSignUp,
326
+ sendOnSignIn: !!options.emailVerification?.sendOnSignIn,
327
+ autoSignInAfterVerification: !!options.emailVerification?.autoSignInAfterVerification,
328
+ expiresIn: options.emailVerification?.expiresIn,
329
+ onEmailVerification: !!options.emailVerification?.onEmailVerification,
330
+ afterEmailVerification: !!options.emailVerification?.afterEmailVerification
331
+ },
332
+ emailAndPassword: {
333
+ enabled: !!options.emailAndPassword?.enabled,
334
+ disableSignUp: !!options.emailAndPassword?.disableSignUp,
335
+ requireEmailVerification: !!options.emailAndPassword?.requireEmailVerification,
336
+ maxPasswordLength: options.emailAndPassword?.maxPasswordLength,
337
+ minPasswordLength: options.emailAndPassword?.minPasswordLength,
338
+ sendResetPassword: !!options.emailAndPassword?.sendResetPassword,
339
+ resetPasswordTokenExpiresIn: options.emailAndPassword?.resetPasswordTokenExpiresIn,
340
+ onPasswordReset: !!options.emailAndPassword?.onPasswordReset,
341
+ password: {
342
+ hash: !!options.emailAndPassword?.password?.hash,
343
+ verify: !!options.emailAndPassword?.password?.verify
344
+ },
345
+ autoSignIn: !!options.emailAndPassword?.autoSignIn,
346
+ revokeSessionsOnPasswordReset: !!options.emailAndPassword?.revokeSessionsOnPasswordReset
347
+ },
348
+ socialProviders: Object.keys(options.socialProviders || {}).map((p) => {
349
+ const provider = options.socialProviders?.[p];
350
+ if (!provider) return {};
351
+ return {
352
+ id: p,
353
+ mapProfileToUser: !!provider.mapProfileToUser,
354
+ disableDefaultScope: !!provider.disableDefaultScope,
355
+ disableIdTokenSignIn: !!provider.disableIdTokenSignIn,
356
+ disableImplicitSignUp: provider.disableImplicitSignUp,
357
+ disableSignUp: provider.disableSignUp,
358
+ getUserInfo: !!provider.getUserInfo,
359
+ overrideUserInfoOnSignIn: !!provider.overrideUserInfoOnSignIn,
360
+ prompt: provider.prompt,
361
+ verifyIdToken: !!provider.verifyIdToken,
362
+ scope: provider.scope,
363
+ refreshAccessToken: !!provider.refreshAccessToken
364
+ };
365
+ }),
366
+ plugins: options.plugins?.map((p) => p.id.toString()),
367
+ user: {
368
+ modelName: options.user?.modelName,
369
+ fields: options.user?.fields,
370
+ additionalFields: options.user?.additionalFields,
371
+ changeEmail: {
372
+ enabled: options.user?.changeEmail?.enabled,
373
+ sendChangeEmailVerification: !!options.user?.changeEmail?.sendChangeEmailVerification
374
+ }
375
+ },
376
+ verification: {
377
+ modelName: options.verification?.modelName,
378
+ disableCleanup: options.verification?.disableCleanup,
379
+ fields: options.verification?.fields
380
+ },
381
+ session: {
382
+ modelName: options.session?.modelName,
383
+ additionalFields: options.session?.additionalFields,
384
+ cookieCache: {
385
+ enabled: options.session?.cookieCache?.enabled,
386
+ maxAge: options.session?.cookieCache?.maxAge
387
+ },
388
+ disableSessionRefresh: options.session?.disableSessionRefresh,
389
+ expiresIn: options.session?.expiresIn,
390
+ fields: options.session?.fields,
391
+ freshAge: options.session?.freshAge,
392
+ preserveSessionInDatabase: options.session?.preserveSessionInDatabase,
393
+ storeSessionInDatabase: options.session?.storeSessionInDatabase,
394
+ updateAge: options.session?.updateAge
395
+ },
396
+ account: {
397
+ modelName: options.account?.modelName,
398
+ fields: options.account?.fields,
399
+ encryptOAuthTokens: options.account?.encryptOAuthTokens,
400
+ updateAccountOnSignIn: options.account?.updateAccountOnSignIn,
401
+ accountLinking: {
402
+ enabled: options.account?.accountLinking?.enabled,
403
+ trustedProviders: options.account?.accountLinking?.trustedProviders,
404
+ updateUserInfoOnLink: options.account?.accountLinking?.updateUserInfoOnLink,
405
+ allowUnlinkingAll: options.account?.accountLinking?.allowUnlinkingAll
406
+ }
407
+ },
408
+ hooks: {
409
+ after: !!options.hooks?.after,
410
+ before: !!options.hooks?.before
411
+ },
412
+ secondaryStorage: !!options.secondaryStorage,
413
+ advanced: {
414
+ cookiePrefix: !!options.advanced?.cookiePrefix,
415
+ //this shouldn't be tracked
416
+ cookies: !!options.advanced?.cookies,
417
+ crossSubDomainCookies: {
418
+ domain: !!options.advanced?.crossSubDomainCookies?.domain,
419
+ enabled: options.advanced?.crossSubDomainCookies?.enabled,
420
+ additionalCookies: options.advanced?.crossSubDomainCookies?.additionalCookies
421
+ },
422
+ database: {
423
+ useNumberId: !!options.advanced?.database?.useNumberId,
424
+ generateId: options.advanced?.database?.generateId,
425
+ defaultFindManyLimit: options.advanced?.database?.defaultFindManyLimit
426
+ },
427
+ useSecureCookies: options.advanced?.useSecureCookies,
428
+ ipAddress: {
429
+ disableIpTracking: options.advanced?.ipAddress?.disableIpTracking,
430
+ ipAddressHeaders: options.advanced?.ipAddress?.ipAddressHeaders
431
+ },
432
+ disableCSRFCheck: options.advanced?.disableCSRFCheck,
433
+ cookieAttributes: {
434
+ expires: options.advanced?.defaultCookieAttributes?.expires,
435
+ secure: options.advanced?.defaultCookieAttributes?.secure,
436
+ sameSite: options.advanced?.defaultCookieAttributes?.sameSite,
437
+ domain: !!options.advanced?.defaultCookieAttributes?.domain,
438
+ path: options.advanced?.defaultCookieAttributes?.path,
439
+ httpOnly: options.advanced?.defaultCookieAttributes?.httpOnly
440
+ }
441
+ },
442
+ trustedOrigins: options.trustedOrigins?.length,
443
+ rateLimit: {
444
+ storage: options.rateLimit?.storage,
445
+ modelName: options.rateLimit?.modelName,
446
+ window: options.rateLimit?.window,
447
+ customStorage: !!options.rateLimit?.customStorage,
448
+ enabled: options.rateLimit?.enabled,
449
+ max: options.rateLimit?.max
450
+ },
451
+ onAPIError: {
452
+ errorURL: options.onAPIError?.errorURL,
453
+ onError: !!options.onAPIError?.onError,
454
+ throw: options.onAPIError?.throw
455
+ },
456
+ logger: {
457
+ disabled: options.logger?.disabled,
458
+ level: options.logger?.level,
459
+ log: !!options.logger?.log
460
+ },
461
+ databaseHooks: {
462
+ user: {
463
+ create: {
464
+ after: !!options.databaseHooks?.user?.create?.after,
465
+ before: !!options.databaseHooks?.user?.create?.before
466
+ },
467
+ update: {
468
+ after: !!options.databaseHooks?.user?.update?.after,
469
+ before: !!options.databaseHooks?.user?.update?.before
470
+ }
471
+ },
472
+ session: {
473
+ create: {
474
+ after: !!options.databaseHooks?.session?.create?.after,
475
+ before: !!options.databaseHooks?.session?.create?.before
476
+ },
477
+ update: {
478
+ after: !!options.databaseHooks?.session?.update?.after,
479
+ before: !!options.databaseHooks?.session?.update?.before
480
+ }
481
+ },
482
+ account: {
483
+ create: {
484
+ after: !!options.databaseHooks?.account?.create?.after,
485
+ before: !!options.databaseHooks?.account?.create?.before
486
+ },
487
+ update: {
488
+ after: !!options.databaseHooks?.account?.update?.after,
489
+ before: !!options.databaseHooks?.account?.update?.before
490
+ }
491
+ },
492
+ verification: {
493
+ create: {
494
+ after: !!options.databaseHooks?.verification?.create?.after,
495
+ before: !!options.databaseHooks?.verification?.create?.before
496
+ },
497
+ update: {
498
+ after: !!options.databaseHooks?.verification?.update?.after,
499
+ before: !!options.databaseHooks?.verification?.update?.before
500
+ }
501
+ }
502
+ }
503
+ };
504
+ }
505
+
506
+ async function createTelemetry(options, context) {
507
+ const debugEnabled = options.telemetry?.debug || env.getBooleanEnvVar("BETTER_AUTH_TELEMETRY_DEBUG", false);
508
+ const TELEMETRY_ENDPOINT = env.ENV.BETTER_AUTH_TELEMETRY_ENDPOINT;
509
+ const track = async (event) => {
510
+ try {
511
+ if (context?.customTrack) {
512
+ await context.customTrack(event);
513
+ } else {
514
+ if (debugEnabled) {
515
+ await Promise.resolve(
516
+ env.logger.info("telemetry event", JSON.stringify(event, null, 2))
517
+ );
518
+ } else {
519
+ await fetch.betterFetch(TELEMETRY_ENDPOINT, {
520
+ method: "POST",
521
+ body: event
522
+ });
523
+ }
524
+ }
525
+ } catch {
526
+ }
527
+ };
528
+ const isEnabled = async () => {
529
+ const telemetryEnabled = options.telemetry?.enabled !== void 0 ? options.telemetry.enabled : false;
530
+ const envEnabled = env.getBooleanEnvVar("BETTER_AUTH_TELEMETRY", false);
531
+ return (envEnabled || telemetryEnabled) && (context?.skipTestCheck || !env.isTest());
532
+ };
533
+ const enabled = await isEnabled();
534
+ let anonymousId;
535
+ if (enabled) {
536
+ anonymousId = await getProjectId(options.baseURL);
537
+ const payload = {
538
+ config: getTelemetryAuthConfig(options),
539
+ runtime: detectRuntime(),
540
+ database: await detectDatabase(),
541
+ framework: await detectFramework(),
542
+ environment: detectEnvironment(),
543
+ systemInfo: await detectSystemInfo(),
544
+ packageManager: detectPackageManager()
545
+ };
546
+ void track({ type: "init", payload, anonymousId });
547
+ }
548
+ return {
549
+ publish: async (event) => {
550
+ if (!enabled) return;
551
+ if (!anonymousId) {
552
+ anonymousId = await getProjectId(options.baseURL);
553
+ }
554
+ await track({
555
+ type: event.type,
556
+ payload: event.payload,
557
+ anonymousId
558
+ });
559
+ }
560
+ };
561
+ }
562
+
563
+ exports.createTelemetry = createTelemetry;
564
+ exports.getTelemetryAuthConfig = getTelemetryAuthConfig;