@bbearai/core 0.2.10 → 0.2.11
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/dist/index.d.mts +2 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.js +171 -166
- package/dist/index.mjs +171 -166
- package/package.json +1 -1
package/dist/index.d.mts
CHANGED
package/dist/index.d.ts
CHANGED
package/dist/index.js
CHANGED
|
@@ -29,6 +29,174 @@ module.exports = __toCommonJS(index_exports);
|
|
|
29
29
|
|
|
30
30
|
// src/client.ts
|
|
31
31
|
var import_supabase_js = require("@supabase/supabase-js");
|
|
32
|
+
|
|
33
|
+
// src/capture.ts
|
|
34
|
+
var MAX_CONSOLE_LOGS = 50;
|
|
35
|
+
var MAX_NETWORK_REQUESTS = 20;
|
|
36
|
+
var ContextCaptureManager = class {
|
|
37
|
+
constructor() {
|
|
38
|
+
this.consoleLogs = [];
|
|
39
|
+
this.networkRequests = [];
|
|
40
|
+
this.originalConsole = {};
|
|
41
|
+
this.isCapturing = false;
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* Start capturing console logs and network requests
|
|
45
|
+
*/
|
|
46
|
+
startCapture() {
|
|
47
|
+
if (this.isCapturing) return;
|
|
48
|
+
this.isCapturing = true;
|
|
49
|
+
this.captureConsole();
|
|
50
|
+
this.captureFetch();
|
|
51
|
+
}
|
|
52
|
+
/**
|
|
53
|
+
* Stop capturing and restore original functions
|
|
54
|
+
*/
|
|
55
|
+
stopCapture() {
|
|
56
|
+
if (!this.isCapturing) return;
|
|
57
|
+
this.isCapturing = false;
|
|
58
|
+
if (this.originalConsole.log) console.log = this.originalConsole.log;
|
|
59
|
+
if (this.originalConsole.warn) console.warn = this.originalConsole.warn;
|
|
60
|
+
if (this.originalConsole.error) console.error = this.originalConsole.error;
|
|
61
|
+
if (this.originalConsole.info) console.info = this.originalConsole.info;
|
|
62
|
+
if (this.originalFetch && typeof window !== "undefined") {
|
|
63
|
+
window.fetch = this.originalFetch;
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
/**
|
|
67
|
+
* Get captured context for a bug report
|
|
68
|
+
*/
|
|
69
|
+
getEnhancedContext() {
|
|
70
|
+
return {
|
|
71
|
+
consoleLogs: [...this.consoleLogs],
|
|
72
|
+
networkRequests: [...this.networkRequests],
|
|
73
|
+
performanceMetrics: this.getPerformanceMetrics(),
|
|
74
|
+
environment: this.getEnvironmentInfo()
|
|
75
|
+
};
|
|
76
|
+
}
|
|
77
|
+
/**
|
|
78
|
+
* Clear captured data
|
|
79
|
+
*/
|
|
80
|
+
clear() {
|
|
81
|
+
this.consoleLogs = [];
|
|
82
|
+
this.networkRequests = [];
|
|
83
|
+
}
|
|
84
|
+
/**
|
|
85
|
+
* Add a log entry manually (for custom logging)
|
|
86
|
+
*/
|
|
87
|
+
addLog(level, message, args) {
|
|
88
|
+
this.consoleLogs.push({
|
|
89
|
+
level,
|
|
90
|
+
message,
|
|
91
|
+
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
92
|
+
args
|
|
93
|
+
});
|
|
94
|
+
if (this.consoleLogs.length > MAX_CONSOLE_LOGS) {
|
|
95
|
+
this.consoleLogs = this.consoleLogs.slice(-MAX_CONSOLE_LOGS);
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
/**
|
|
99
|
+
* Add a network request manually
|
|
100
|
+
*/
|
|
101
|
+
addNetworkRequest(request) {
|
|
102
|
+
this.networkRequests.push(request);
|
|
103
|
+
if (this.networkRequests.length > MAX_NETWORK_REQUESTS) {
|
|
104
|
+
this.networkRequests = this.networkRequests.slice(-MAX_NETWORK_REQUESTS);
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
captureConsole() {
|
|
108
|
+
if (typeof console === "undefined") return;
|
|
109
|
+
const levels = ["log", "warn", "error", "info"];
|
|
110
|
+
levels.forEach((level) => {
|
|
111
|
+
this.originalConsole[level] = console[level];
|
|
112
|
+
console[level] = (...args) => {
|
|
113
|
+
this.originalConsole[level]?.apply(console, args);
|
|
114
|
+
try {
|
|
115
|
+
const message = args.map((arg) => {
|
|
116
|
+
if (typeof arg === "string") return arg;
|
|
117
|
+
try {
|
|
118
|
+
return JSON.stringify(arg);
|
|
119
|
+
} catch {
|
|
120
|
+
return String(arg);
|
|
121
|
+
}
|
|
122
|
+
}).join(" ");
|
|
123
|
+
this.addLog(level, message.slice(0, 500));
|
|
124
|
+
} catch {
|
|
125
|
+
}
|
|
126
|
+
};
|
|
127
|
+
});
|
|
128
|
+
}
|
|
129
|
+
captureFetch() {
|
|
130
|
+
if (typeof window === "undefined" || typeof fetch === "undefined") return;
|
|
131
|
+
this.originalFetch = window.fetch;
|
|
132
|
+
const self = this;
|
|
133
|
+
window.fetch = async function(input, init) {
|
|
134
|
+
const startTime = Date.now();
|
|
135
|
+
const url = typeof input === "string" ? input : input instanceof URL ? input.toString() : input.url;
|
|
136
|
+
const method = init?.method || "GET";
|
|
137
|
+
try {
|
|
138
|
+
const response = await self.originalFetch.call(window, input, init);
|
|
139
|
+
self.addNetworkRequest({
|
|
140
|
+
method,
|
|
141
|
+
url: url.slice(0, 200),
|
|
142
|
+
// Limit URL length
|
|
143
|
+
status: response.status,
|
|
144
|
+
duration: Date.now() - startTime,
|
|
145
|
+
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
146
|
+
});
|
|
147
|
+
return response;
|
|
148
|
+
} catch (error) {
|
|
149
|
+
self.addNetworkRequest({
|
|
150
|
+
method,
|
|
151
|
+
url: url.slice(0, 200),
|
|
152
|
+
duration: Date.now() - startTime,
|
|
153
|
+
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
154
|
+
error: error instanceof Error ? error.message : "Unknown error"
|
|
155
|
+
});
|
|
156
|
+
throw error;
|
|
157
|
+
}
|
|
158
|
+
};
|
|
159
|
+
}
|
|
160
|
+
getPerformanceMetrics() {
|
|
161
|
+
if (typeof window === "undefined" || typeof performance === "undefined") return void 0;
|
|
162
|
+
const metrics = {};
|
|
163
|
+
try {
|
|
164
|
+
const navigation = performance.getEntriesByType("navigation")[0];
|
|
165
|
+
if (navigation) {
|
|
166
|
+
metrics.pageLoadTime = Math.round(navigation.loadEventEnd - navigation.startTime);
|
|
167
|
+
}
|
|
168
|
+
} catch {
|
|
169
|
+
}
|
|
170
|
+
try {
|
|
171
|
+
const memory = performance.memory;
|
|
172
|
+
if (memory) {
|
|
173
|
+
metrics.memoryUsage = Math.round(memory.usedJSHeapSize / 1024 / 1024);
|
|
174
|
+
}
|
|
175
|
+
} catch {
|
|
176
|
+
}
|
|
177
|
+
return Object.keys(metrics).length > 0 ? metrics : void 0;
|
|
178
|
+
}
|
|
179
|
+
getEnvironmentInfo() {
|
|
180
|
+
if (typeof window === "undefined" || typeof navigator === "undefined") return void 0;
|
|
181
|
+
return {
|
|
182
|
+
language: navigator.language,
|
|
183
|
+
timezone: Intl.DateTimeFormat().resolvedOptions().timeZone,
|
|
184
|
+
cookiesEnabled: navigator.cookieEnabled,
|
|
185
|
+
localStorage: typeof localStorage !== "undefined",
|
|
186
|
+
online: navigator.onLine
|
|
187
|
+
};
|
|
188
|
+
}
|
|
189
|
+
};
|
|
190
|
+
var contextCapture = new ContextCaptureManager();
|
|
191
|
+
function captureError(error, errorInfo) {
|
|
192
|
+
return {
|
|
193
|
+
errorMessage: error.message,
|
|
194
|
+
errorStack: error.stack,
|
|
195
|
+
componentStack: errorInfo?.componentStack
|
|
196
|
+
};
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
// src/client.ts
|
|
32
200
|
var DEFAULT_SUPABASE_URL = "https://kyxgzjnqgvapvlnvqawz.supabase.co";
|
|
33
201
|
var getEnvVar = (key) => {
|
|
34
202
|
try {
|
|
@@ -105,6 +273,8 @@ var BugBearClient = class {
|
|
|
105
273
|
project_id: this.config.projectId,
|
|
106
274
|
reporter_id: userInfo.id,
|
|
107
275
|
// User ID from host app (required)
|
|
276
|
+
reporter_name: testerInfo?.name || userInfo.name || null,
|
|
277
|
+
reporter_email: userInfo.email || null,
|
|
108
278
|
tester_id: testerInfo?.id || null,
|
|
109
279
|
// Tester record ID (optional)
|
|
110
280
|
report_type: report.type,
|
|
@@ -118,6 +288,7 @@ var BugBearClient = class {
|
|
|
118
288
|
app_context: report.appContext,
|
|
119
289
|
device_info: report.deviceInfo || this.getDeviceInfo(),
|
|
120
290
|
navigation_history: this.getNavigationHistory(),
|
|
291
|
+
enhanced_context: report.enhancedContext || contextCapture.getEnhancedContext(),
|
|
121
292
|
assignment_id: report.assignmentId,
|
|
122
293
|
test_case_id: report.testCaseId
|
|
123
294
|
};
|
|
@@ -1351,172 +1522,6 @@ var BugBearClient = class {
|
|
|
1351
1522
|
function createBugBear(config) {
|
|
1352
1523
|
return new BugBearClient(config);
|
|
1353
1524
|
}
|
|
1354
|
-
|
|
1355
|
-
// src/capture.ts
|
|
1356
|
-
var MAX_CONSOLE_LOGS = 50;
|
|
1357
|
-
var MAX_NETWORK_REQUESTS = 20;
|
|
1358
|
-
var ContextCaptureManager = class {
|
|
1359
|
-
constructor() {
|
|
1360
|
-
this.consoleLogs = [];
|
|
1361
|
-
this.networkRequests = [];
|
|
1362
|
-
this.originalConsole = {};
|
|
1363
|
-
this.isCapturing = false;
|
|
1364
|
-
}
|
|
1365
|
-
/**
|
|
1366
|
-
* Start capturing console logs and network requests
|
|
1367
|
-
*/
|
|
1368
|
-
startCapture() {
|
|
1369
|
-
if (this.isCapturing) return;
|
|
1370
|
-
this.isCapturing = true;
|
|
1371
|
-
this.captureConsole();
|
|
1372
|
-
this.captureFetch();
|
|
1373
|
-
}
|
|
1374
|
-
/**
|
|
1375
|
-
* Stop capturing and restore original functions
|
|
1376
|
-
*/
|
|
1377
|
-
stopCapture() {
|
|
1378
|
-
if (!this.isCapturing) return;
|
|
1379
|
-
this.isCapturing = false;
|
|
1380
|
-
if (this.originalConsole.log) console.log = this.originalConsole.log;
|
|
1381
|
-
if (this.originalConsole.warn) console.warn = this.originalConsole.warn;
|
|
1382
|
-
if (this.originalConsole.error) console.error = this.originalConsole.error;
|
|
1383
|
-
if (this.originalConsole.info) console.info = this.originalConsole.info;
|
|
1384
|
-
if (this.originalFetch && typeof window !== "undefined") {
|
|
1385
|
-
window.fetch = this.originalFetch;
|
|
1386
|
-
}
|
|
1387
|
-
}
|
|
1388
|
-
/**
|
|
1389
|
-
* Get captured context for a bug report
|
|
1390
|
-
*/
|
|
1391
|
-
getEnhancedContext() {
|
|
1392
|
-
return {
|
|
1393
|
-
consoleLogs: [...this.consoleLogs],
|
|
1394
|
-
networkRequests: [...this.networkRequests],
|
|
1395
|
-
performanceMetrics: this.getPerformanceMetrics(),
|
|
1396
|
-
environment: this.getEnvironmentInfo()
|
|
1397
|
-
};
|
|
1398
|
-
}
|
|
1399
|
-
/**
|
|
1400
|
-
* Clear captured data
|
|
1401
|
-
*/
|
|
1402
|
-
clear() {
|
|
1403
|
-
this.consoleLogs = [];
|
|
1404
|
-
this.networkRequests = [];
|
|
1405
|
-
}
|
|
1406
|
-
/**
|
|
1407
|
-
* Add a log entry manually (for custom logging)
|
|
1408
|
-
*/
|
|
1409
|
-
addLog(level, message, args) {
|
|
1410
|
-
this.consoleLogs.push({
|
|
1411
|
-
level,
|
|
1412
|
-
message,
|
|
1413
|
-
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
1414
|
-
args
|
|
1415
|
-
});
|
|
1416
|
-
if (this.consoleLogs.length > MAX_CONSOLE_LOGS) {
|
|
1417
|
-
this.consoleLogs = this.consoleLogs.slice(-MAX_CONSOLE_LOGS);
|
|
1418
|
-
}
|
|
1419
|
-
}
|
|
1420
|
-
/**
|
|
1421
|
-
* Add a network request manually
|
|
1422
|
-
*/
|
|
1423
|
-
addNetworkRequest(request) {
|
|
1424
|
-
this.networkRequests.push(request);
|
|
1425
|
-
if (this.networkRequests.length > MAX_NETWORK_REQUESTS) {
|
|
1426
|
-
this.networkRequests = this.networkRequests.slice(-MAX_NETWORK_REQUESTS);
|
|
1427
|
-
}
|
|
1428
|
-
}
|
|
1429
|
-
captureConsole() {
|
|
1430
|
-
if (typeof console === "undefined") return;
|
|
1431
|
-
const levels = ["log", "warn", "error", "info"];
|
|
1432
|
-
levels.forEach((level) => {
|
|
1433
|
-
this.originalConsole[level] = console[level];
|
|
1434
|
-
console[level] = (...args) => {
|
|
1435
|
-
this.originalConsole[level]?.apply(console, args);
|
|
1436
|
-
try {
|
|
1437
|
-
const message = args.map((arg) => {
|
|
1438
|
-
if (typeof arg === "string") return arg;
|
|
1439
|
-
try {
|
|
1440
|
-
return JSON.stringify(arg);
|
|
1441
|
-
} catch {
|
|
1442
|
-
return String(arg);
|
|
1443
|
-
}
|
|
1444
|
-
}).join(" ");
|
|
1445
|
-
this.addLog(level, message.slice(0, 500));
|
|
1446
|
-
} catch {
|
|
1447
|
-
}
|
|
1448
|
-
};
|
|
1449
|
-
});
|
|
1450
|
-
}
|
|
1451
|
-
captureFetch() {
|
|
1452
|
-
if (typeof window === "undefined" || typeof fetch === "undefined") return;
|
|
1453
|
-
this.originalFetch = window.fetch;
|
|
1454
|
-
const self = this;
|
|
1455
|
-
window.fetch = async function(input, init) {
|
|
1456
|
-
const startTime = Date.now();
|
|
1457
|
-
const url = typeof input === "string" ? input : input instanceof URL ? input.toString() : input.url;
|
|
1458
|
-
const method = init?.method || "GET";
|
|
1459
|
-
try {
|
|
1460
|
-
const response = await self.originalFetch.call(window, input, init);
|
|
1461
|
-
self.addNetworkRequest({
|
|
1462
|
-
method,
|
|
1463
|
-
url: url.slice(0, 200),
|
|
1464
|
-
// Limit URL length
|
|
1465
|
-
status: response.status,
|
|
1466
|
-
duration: Date.now() - startTime,
|
|
1467
|
-
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
1468
|
-
});
|
|
1469
|
-
return response;
|
|
1470
|
-
} catch (error) {
|
|
1471
|
-
self.addNetworkRequest({
|
|
1472
|
-
method,
|
|
1473
|
-
url: url.slice(0, 200),
|
|
1474
|
-
duration: Date.now() - startTime,
|
|
1475
|
-
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
1476
|
-
error: error instanceof Error ? error.message : "Unknown error"
|
|
1477
|
-
});
|
|
1478
|
-
throw error;
|
|
1479
|
-
}
|
|
1480
|
-
};
|
|
1481
|
-
}
|
|
1482
|
-
getPerformanceMetrics() {
|
|
1483
|
-
if (typeof window === "undefined" || typeof performance === "undefined") return void 0;
|
|
1484
|
-
const metrics = {};
|
|
1485
|
-
try {
|
|
1486
|
-
const navigation = performance.getEntriesByType("navigation")[0];
|
|
1487
|
-
if (navigation) {
|
|
1488
|
-
metrics.pageLoadTime = Math.round(navigation.loadEventEnd - navigation.startTime);
|
|
1489
|
-
}
|
|
1490
|
-
} catch {
|
|
1491
|
-
}
|
|
1492
|
-
try {
|
|
1493
|
-
const memory = performance.memory;
|
|
1494
|
-
if (memory) {
|
|
1495
|
-
metrics.memoryUsage = Math.round(memory.usedJSHeapSize / 1024 / 1024);
|
|
1496
|
-
}
|
|
1497
|
-
} catch {
|
|
1498
|
-
}
|
|
1499
|
-
return Object.keys(metrics).length > 0 ? metrics : void 0;
|
|
1500
|
-
}
|
|
1501
|
-
getEnvironmentInfo() {
|
|
1502
|
-
if (typeof window === "undefined" || typeof navigator === "undefined") return void 0;
|
|
1503
|
-
return {
|
|
1504
|
-
language: navigator.language,
|
|
1505
|
-
timezone: Intl.DateTimeFormat().resolvedOptions().timeZone,
|
|
1506
|
-
cookiesEnabled: navigator.cookieEnabled,
|
|
1507
|
-
localStorage: typeof localStorage !== "undefined",
|
|
1508
|
-
online: navigator.onLine
|
|
1509
|
-
};
|
|
1510
|
-
}
|
|
1511
|
-
};
|
|
1512
|
-
var contextCapture = new ContextCaptureManager();
|
|
1513
|
-
function captureError(error, errorInfo) {
|
|
1514
|
-
return {
|
|
1515
|
-
errorMessage: error.message,
|
|
1516
|
-
errorStack: error.stack,
|
|
1517
|
-
componentStack: errorInfo?.componentStack
|
|
1518
|
-
};
|
|
1519
|
-
}
|
|
1520
1525
|
// Annotate the CommonJS export names for ESM import in node:
|
|
1521
1526
|
0 && (module.exports = {
|
|
1522
1527
|
BugBearClient,
|
package/dist/index.mjs
CHANGED
|
@@ -1,5 +1,173 @@
|
|
|
1
1
|
// src/client.ts
|
|
2
2
|
import { createClient } from "@supabase/supabase-js";
|
|
3
|
+
|
|
4
|
+
// src/capture.ts
|
|
5
|
+
var MAX_CONSOLE_LOGS = 50;
|
|
6
|
+
var MAX_NETWORK_REQUESTS = 20;
|
|
7
|
+
var ContextCaptureManager = class {
|
|
8
|
+
constructor() {
|
|
9
|
+
this.consoleLogs = [];
|
|
10
|
+
this.networkRequests = [];
|
|
11
|
+
this.originalConsole = {};
|
|
12
|
+
this.isCapturing = false;
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* Start capturing console logs and network requests
|
|
16
|
+
*/
|
|
17
|
+
startCapture() {
|
|
18
|
+
if (this.isCapturing) return;
|
|
19
|
+
this.isCapturing = true;
|
|
20
|
+
this.captureConsole();
|
|
21
|
+
this.captureFetch();
|
|
22
|
+
}
|
|
23
|
+
/**
|
|
24
|
+
* Stop capturing and restore original functions
|
|
25
|
+
*/
|
|
26
|
+
stopCapture() {
|
|
27
|
+
if (!this.isCapturing) return;
|
|
28
|
+
this.isCapturing = false;
|
|
29
|
+
if (this.originalConsole.log) console.log = this.originalConsole.log;
|
|
30
|
+
if (this.originalConsole.warn) console.warn = this.originalConsole.warn;
|
|
31
|
+
if (this.originalConsole.error) console.error = this.originalConsole.error;
|
|
32
|
+
if (this.originalConsole.info) console.info = this.originalConsole.info;
|
|
33
|
+
if (this.originalFetch && typeof window !== "undefined") {
|
|
34
|
+
window.fetch = this.originalFetch;
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
/**
|
|
38
|
+
* Get captured context for a bug report
|
|
39
|
+
*/
|
|
40
|
+
getEnhancedContext() {
|
|
41
|
+
return {
|
|
42
|
+
consoleLogs: [...this.consoleLogs],
|
|
43
|
+
networkRequests: [...this.networkRequests],
|
|
44
|
+
performanceMetrics: this.getPerformanceMetrics(),
|
|
45
|
+
environment: this.getEnvironmentInfo()
|
|
46
|
+
};
|
|
47
|
+
}
|
|
48
|
+
/**
|
|
49
|
+
* Clear captured data
|
|
50
|
+
*/
|
|
51
|
+
clear() {
|
|
52
|
+
this.consoleLogs = [];
|
|
53
|
+
this.networkRequests = [];
|
|
54
|
+
}
|
|
55
|
+
/**
|
|
56
|
+
* Add a log entry manually (for custom logging)
|
|
57
|
+
*/
|
|
58
|
+
addLog(level, message, args) {
|
|
59
|
+
this.consoleLogs.push({
|
|
60
|
+
level,
|
|
61
|
+
message,
|
|
62
|
+
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
63
|
+
args
|
|
64
|
+
});
|
|
65
|
+
if (this.consoleLogs.length > MAX_CONSOLE_LOGS) {
|
|
66
|
+
this.consoleLogs = this.consoleLogs.slice(-MAX_CONSOLE_LOGS);
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
/**
|
|
70
|
+
* Add a network request manually
|
|
71
|
+
*/
|
|
72
|
+
addNetworkRequest(request) {
|
|
73
|
+
this.networkRequests.push(request);
|
|
74
|
+
if (this.networkRequests.length > MAX_NETWORK_REQUESTS) {
|
|
75
|
+
this.networkRequests = this.networkRequests.slice(-MAX_NETWORK_REQUESTS);
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
captureConsole() {
|
|
79
|
+
if (typeof console === "undefined") return;
|
|
80
|
+
const levels = ["log", "warn", "error", "info"];
|
|
81
|
+
levels.forEach((level) => {
|
|
82
|
+
this.originalConsole[level] = console[level];
|
|
83
|
+
console[level] = (...args) => {
|
|
84
|
+
this.originalConsole[level]?.apply(console, args);
|
|
85
|
+
try {
|
|
86
|
+
const message = args.map((arg) => {
|
|
87
|
+
if (typeof arg === "string") return arg;
|
|
88
|
+
try {
|
|
89
|
+
return JSON.stringify(arg);
|
|
90
|
+
} catch {
|
|
91
|
+
return String(arg);
|
|
92
|
+
}
|
|
93
|
+
}).join(" ");
|
|
94
|
+
this.addLog(level, message.slice(0, 500));
|
|
95
|
+
} catch {
|
|
96
|
+
}
|
|
97
|
+
};
|
|
98
|
+
});
|
|
99
|
+
}
|
|
100
|
+
captureFetch() {
|
|
101
|
+
if (typeof window === "undefined" || typeof fetch === "undefined") return;
|
|
102
|
+
this.originalFetch = window.fetch;
|
|
103
|
+
const self = this;
|
|
104
|
+
window.fetch = async function(input, init) {
|
|
105
|
+
const startTime = Date.now();
|
|
106
|
+
const url = typeof input === "string" ? input : input instanceof URL ? input.toString() : input.url;
|
|
107
|
+
const method = init?.method || "GET";
|
|
108
|
+
try {
|
|
109
|
+
const response = await self.originalFetch.call(window, input, init);
|
|
110
|
+
self.addNetworkRequest({
|
|
111
|
+
method,
|
|
112
|
+
url: url.slice(0, 200),
|
|
113
|
+
// Limit URL length
|
|
114
|
+
status: response.status,
|
|
115
|
+
duration: Date.now() - startTime,
|
|
116
|
+
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
117
|
+
});
|
|
118
|
+
return response;
|
|
119
|
+
} catch (error) {
|
|
120
|
+
self.addNetworkRequest({
|
|
121
|
+
method,
|
|
122
|
+
url: url.slice(0, 200),
|
|
123
|
+
duration: Date.now() - startTime,
|
|
124
|
+
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
125
|
+
error: error instanceof Error ? error.message : "Unknown error"
|
|
126
|
+
});
|
|
127
|
+
throw error;
|
|
128
|
+
}
|
|
129
|
+
};
|
|
130
|
+
}
|
|
131
|
+
getPerformanceMetrics() {
|
|
132
|
+
if (typeof window === "undefined" || typeof performance === "undefined") return void 0;
|
|
133
|
+
const metrics = {};
|
|
134
|
+
try {
|
|
135
|
+
const navigation = performance.getEntriesByType("navigation")[0];
|
|
136
|
+
if (navigation) {
|
|
137
|
+
metrics.pageLoadTime = Math.round(navigation.loadEventEnd - navigation.startTime);
|
|
138
|
+
}
|
|
139
|
+
} catch {
|
|
140
|
+
}
|
|
141
|
+
try {
|
|
142
|
+
const memory = performance.memory;
|
|
143
|
+
if (memory) {
|
|
144
|
+
metrics.memoryUsage = Math.round(memory.usedJSHeapSize / 1024 / 1024);
|
|
145
|
+
}
|
|
146
|
+
} catch {
|
|
147
|
+
}
|
|
148
|
+
return Object.keys(metrics).length > 0 ? metrics : void 0;
|
|
149
|
+
}
|
|
150
|
+
getEnvironmentInfo() {
|
|
151
|
+
if (typeof window === "undefined" || typeof navigator === "undefined") return void 0;
|
|
152
|
+
return {
|
|
153
|
+
language: navigator.language,
|
|
154
|
+
timezone: Intl.DateTimeFormat().resolvedOptions().timeZone,
|
|
155
|
+
cookiesEnabled: navigator.cookieEnabled,
|
|
156
|
+
localStorage: typeof localStorage !== "undefined",
|
|
157
|
+
online: navigator.onLine
|
|
158
|
+
};
|
|
159
|
+
}
|
|
160
|
+
};
|
|
161
|
+
var contextCapture = new ContextCaptureManager();
|
|
162
|
+
function captureError(error, errorInfo) {
|
|
163
|
+
return {
|
|
164
|
+
errorMessage: error.message,
|
|
165
|
+
errorStack: error.stack,
|
|
166
|
+
componentStack: errorInfo?.componentStack
|
|
167
|
+
};
|
|
168
|
+
}
|
|
169
|
+
|
|
170
|
+
// src/client.ts
|
|
3
171
|
var DEFAULT_SUPABASE_URL = "https://kyxgzjnqgvapvlnvqawz.supabase.co";
|
|
4
172
|
var getEnvVar = (key) => {
|
|
5
173
|
try {
|
|
@@ -76,6 +244,8 @@ var BugBearClient = class {
|
|
|
76
244
|
project_id: this.config.projectId,
|
|
77
245
|
reporter_id: userInfo.id,
|
|
78
246
|
// User ID from host app (required)
|
|
247
|
+
reporter_name: testerInfo?.name || userInfo.name || null,
|
|
248
|
+
reporter_email: userInfo.email || null,
|
|
79
249
|
tester_id: testerInfo?.id || null,
|
|
80
250
|
// Tester record ID (optional)
|
|
81
251
|
report_type: report.type,
|
|
@@ -89,6 +259,7 @@ var BugBearClient = class {
|
|
|
89
259
|
app_context: report.appContext,
|
|
90
260
|
device_info: report.deviceInfo || this.getDeviceInfo(),
|
|
91
261
|
navigation_history: this.getNavigationHistory(),
|
|
262
|
+
enhanced_context: report.enhancedContext || contextCapture.getEnhancedContext(),
|
|
92
263
|
assignment_id: report.assignmentId,
|
|
93
264
|
test_case_id: report.testCaseId
|
|
94
265
|
};
|
|
@@ -1322,172 +1493,6 @@ var BugBearClient = class {
|
|
|
1322
1493
|
function createBugBear(config) {
|
|
1323
1494
|
return new BugBearClient(config);
|
|
1324
1495
|
}
|
|
1325
|
-
|
|
1326
|
-
// src/capture.ts
|
|
1327
|
-
var MAX_CONSOLE_LOGS = 50;
|
|
1328
|
-
var MAX_NETWORK_REQUESTS = 20;
|
|
1329
|
-
var ContextCaptureManager = class {
|
|
1330
|
-
constructor() {
|
|
1331
|
-
this.consoleLogs = [];
|
|
1332
|
-
this.networkRequests = [];
|
|
1333
|
-
this.originalConsole = {};
|
|
1334
|
-
this.isCapturing = false;
|
|
1335
|
-
}
|
|
1336
|
-
/**
|
|
1337
|
-
* Start capturing console logs and network requests
|
|
1338
|
-
*/
|
|
1339
|
-
startCapture() {
|
|
1340
|
-
if (this.isCapturing) return;
|
|
1341
|
-
this.isCapturing = true;
|
|
1342
|
-
this.captureConsole();
|
|
1343
|
-
this.captureFetch();
|
|
1344
|
-
}
|
|
1345
|
-
/**
|
|
1346
|
-
* Stop capturing and restore original functions
|
|
1347
|
-
*/
|
|
1348
|
-
stopCapture() {
|
|
1349
|
-
if (!this.isCapturing) return;
|
|
1350
|
-
this.isCapturing = false;
|
|
1351
|
-
if (this.originalConsole.log) console.log = this.originalConsole.log;
|
|
1352
|
-
if (this.originalConsole.warn) console.warn = this.originalConsole.warn;
|
|
1353
|
-
if (this.originalConsole.error) console.error = this.originalConsole.error;
|
|
1354
|
-
if (this.originalConsole.info) console.info = this.originalConsole.info;
|
|
1355
|
-
if (this.originalFetch && typeof window !== "undefined") {
|
|
1356
|
-
window.fetch = this.originalFetch;
|
|
1357
|
-
}
|
|
1358
|
-
}
|
|
1359
|
-
/**
|
|
1360
|
-
* Get captured context for a bug report
|
|
1361
|
-
*/
|
|
1362
|
-
getEnhancedContext() {
|
|
1363
|
-
return {
|
|
1364
|
-
consoleLogs: [...this.consoleLogs],
|
|
1365
|
-
networkRequests: [...this.networkRequests],
|
|
1366
|
-
performanceMetrics: this.getPerformanceMetrics(),
|
|
1367
|
-
environment: this.getEnvironmentInfo()
|
|
1368
|
-
};
|
|
1369
|
-
}
|
|
1370
|
-
/**
|
|
1371
|
-
* Clear captured data
|
|
1372
|
-
*/
|
|
1373
|
-
clear() {
|
|
1374
|
-
this.consoleLogs = [];
|
|
1375
|
-
this.networkRequests = [];
|
|
1376
|
-
}
|
|
1377
|
-
/**
|
|
1378
|
-
* Add a log entry manually (for custom logging)
|
|
1379
|
-
*/
|
|
1380
|
-
addLog(level, message, args) {
|
|
1381
|
-
this.consoleLogs.push({
|
|
1382
|
-
level,
|
|
1383
|
-
message,
|
|
1384
|
-
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
1385
|
-
args
|
|
1386
|
-
});
|
|
1387
|
-
if (this.consoleLogs.length > MAX_CONSOLE_LOGS) {
|
|
1388
|
-
this.consoleLogs = this.consoleLogs.slice(-MAX_CONSOLE_LOGS);
|
|
1389
|
-
}
|
|
1390
|
-
}
|
|
1391
|
-
/**
|
|
1392
|
-
* Add a network request manually
|
|
1393
|
-
*/
|
|
1394
|
-
addNetworkRequest(request) {
|
|
1395
|
-
this.networkRequests.push(request);
|
|
1396
|
-
if (this.networkRequests.length > MAX_NETWORK_REQUESTS) {
|
|
1397
|
-
this.networkRequests = this.networkRequests.slice(-MAX_NETWORK_REQUESTS);
|
|
1398
|
-
}
|
|
1399
|
-
}
|
|
1400
|
-
captureConsole() {
|
|
1401
|
-
if (typeof console === "undefined") return;
|
|
1402
|
-
const levels = ["log", "warn", "error", "info"];
|
|
1403
|
-
levels.forEach((level) => {
|
|
1404
|
-
this.originalConsole[level] = console[level];
|
|
1405
|
-
console[level] = (...args) => {
|
|
1406
|
-
this.originalConsole[level]?.apply(console, args);
|
|
1407
|
-
try {
|
|
1408
|
-
const message = args.map((arg) => {
|
|
1409
|
-
if (typeof arg === "string") return arg;
|
|
1410
|
-
try {
|
|
1411
|
-
return JSON.stringify(arg);
|
|
1412
|
-
} catch {
|
|
1413
|
-
return String(arg);
|
|
1414
|
-
}
|
|
1415
|
-
}).join(" ");
|
|
1416
|
-
this.addLog(level, message.slice(0, 500));
|
|
1417
|
-
} catch {
|
|
1418
|
-
}
|
|
1419
|
-
};
|
|
1420
|
-
});
|
|
1421
|
-
}
|
|
1422
|
-
captureFetch() {
|
|
1423
|
-
if (typeof window === "undefined" || typeof fetch === "undefined") return;
|
|
1424
|
-
this.originalFetch = window.fetch;
|
|
1425
|
-
const self = this;
|
|
1426
|
-
window.fetch = async function(input, init) {
|
|
1427
|
-
const startTime = Date.now();
|
|
1428
|
-
const url = typeof input === "string" ? input : input instanceof URL ? input.toString() : input.url;
|
|
1429
|
-
const method = init?.method || "GET";
|
|
1430
|
-
try {
|
|
1431
|
-
const response = await self.originalFetch.call(window, input, init);
|
|
1432
|
-
self.addNetworkRequest({
|
|
1433
|
-
method,
|
|
1434
|
-
url: url.slice(0, 200),
|
|
1435
|
-
// Limit URL length
|
|
1436
|
-
status: response.status,
|
|
1437
|
-
duration: Date.now() - startTime,
|
|
1438
|
-
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
1439
|
-
});
|
|
1440
|
-
return response;
|
|
1441
|
-
} catch (error) {
|
|
1442
|
-
self.addNetworkRequest({
|
|
1443
|
-
method,
|
|
1444
|
-
url: url.slice(0, 200),
|
|
1445
|
-
duration: Date.now() - startTime,
|
|
1446
|
-
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
1447
|
-
error: error instanceof Error ? error.message : "Unknown error"
|
|
1448
|
-
});
|
|
1449
|
-
throw error;
|
|
1450
|
-
}
|
|
1451
|
-
};
|
|
1452
|
-
}
|
|
1453
|
-
getPerformanceMetrics() {
|
|
1454
|
-
if (typeof window === "undefined" || typeof performance === "undefined") return void 0;
|
|
1455
|
-
const metrics = {};
|
|
1456
|
-
try {
|
|
1457
|
-
const navigation = performance.getEntriesByType("navigation")[0];
|
|
1458
|
-
if (navigation) {
|
|
1459
|
-
metrics.pageLoadTime = Math.round(navigation.loadEventEnd - navigation.startTime);
|
|
1460
|
-
}
|
|
1461
|
-
} catch {
|
|
1462
|
-
}
|
|
1463
|
-
try {
|
|
1464
|
-
const memory = performance.memory;
|
|
1465
|
-
if (memory) {
|
|
1466
|
-
metrics.memoryUsage = Math.round(memory.usedJSHeapSize / 1024 / 1024);
|
|
1467
|
-
}
|
|
1468
|
-
} catch {
|
|
1469
|
-
}
|
|
1470
|
-
return Object.keys(metrics).length > 0 ? metrics : void 0;
|
|
1471
|
-
}
|
|
1472
|
-
getEnvironmentInfo() {
|
|
1473
|
-
if (typeof window === "undefined" || typeof navigator === "undefined") return void 0;
|
|
1474
|
-
return {
|
|
1475
|
-
language: navigator.language,
|
|
1476
|
-
timezone: Intl.DateTimeFormat().resolvedOptions().timeZone,
|
|
1477
|
-
cookiesEnabled: navigator.cookieEnabled,
|
|
1478
|
-
localStorage: typeof localStorage !== "undefined",
|
|
1479
|
-
online: navigator.onLine
|
|
1480
|
-
};
|
|
1481
|
-
}
|
|
1482
|
-
};
|
|
1483
|
-
var contextCapture = new ContextCaptureManager();
|
|
1484
|
-
function captureError(error, errorInfo) {
|
|
1485
|
-
return {
|
|
1486
|
-
errorMessage: error.message,
|
|
1487
|
-
errorStack: error.stack,
|
|
1488
|
-
componentStack: errorInfo?.componentStack
|
|
1489
|
-
};
|
|
1490
|
-
}
|
|
1491
1496
|
export {
|
|
1492
1497
|
BugBearClient,
|
|
1493
1498
|
captureError,
|