@bbearai/core 0.2.11 → 0.2.12

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 CHANGED
@@ -39,6 +39,8 @@ interface NetworkRequest {
39
39
  duration?: number;
40
40
  timestamp: string;
41
41
  error?: string;
42
+ /** Truncated response body for failed requests (4xx/5xx) */
43
+ responseBody?: string;
42
44
  }
43
45
  /** Enhanced bug context for detailed debugging */
44
46
  interface EnhancedBugContext {
@@ -46,6 +48,8 @@ interface EnhancedBugContext {
46
48
  consoleLogs?: ConsoleLogEntry[];
47
49
  /** Recent network requests (last 20) */
48
50
  networkRequests?: NetworkRequest[];
51
+ /** Auto-captured navigation history (last 20 route changes) */
52
+ navigationHistory?: string[];
49
53
  /** Current Redux/state snapshot (serialized) */
50
54
  stateSnapshot?: Record<string, unknown>;
51
55
  /** Performance metrics */
@@ -602,13 +606,20 @@ declare class BugBearClient {
602
606
  private navigationHistory;
603
607
  constructor(config: BugBearConfig);
604
608
  /**
605
- * Track navigation for context
609
+ * Track navigation for context.
610
+ * Also forwards to contextCapture for auto-tracked navigation.
606
611
  */
607
612
  trackNavigation(route: string): void;
608
613
  /**
609
- * Get current navigation history
614
+ * Get current navigation history.
615
+ * Priority: config callback > manual tracking > auto-captured (pushState/popstate)
610
616
  */
611
617
  getNavigationHistory(): string[];
618
+ /**
619
+ * Get current app context.
620
+ * Uses config.getAppContext() callback if provided, otherwise builds from available data.
621
+ */
622
+ getAppContext(): AppContext;
612
623
  /**
613
624
  * Get current user info from host app or BugBear's own auth
614
625
  */
@@ -892,16 +903,21 @@ declare function createBugBear(config: BugBearConfig): BugBearClient;
892
903
  */
893
904
 
894
905
  /**
895
- * Context capture singleton that captures console logs and network requests
906
+ * Context capture singleton that captures console logs, network requests,
907
+ * and navigation history automatically.
896
908
  */
897
909
  declare class ContextCaptureManager {
898
910
  private consoleLogs;
899
911
  private networkRequests;
912
+ private navigationHistory;
900
913
  private originalConsole;
901
914
  private originalFetch?;
915
+ private originalPushState?;
916
+ private originalReplaceState?;
917
+ private popstateHandler?;
902
918
  private isCapturing;
903
919
  /**
904
- * Start capturing console logs and network requests
920
+ * Start capturing console logs, network requests, and navigation
905
921
  */
906
922
  startCapture(): void;
907
923
  /**
@@ -912,6 +928,18 @@ declare class ContextCaptureManager {
912
928
  * Get captured context for a bug report
913
929
  */
914
930
  getEnhancedContext(): EnhancedBugContext;
931
+ /**
932
+ * Get the auto-captured navigation history
933
+ */
934
+ getNavigationHistory(): string[];
935
+ /**
936
+ * Get the current route (last entry in navigation history, or window.location)
937
+ */
938
+ getCurrentRoute(): string;
939
+ /**
940
+ * Manually track a navigation event (for React Native or custom routing)
941
+ */
942
+ trackNavigation(route: string): void;
915
943
  /**
916
944
  * Clear captured data
917
945
  */
@@ -926,6 +954,7 @@ declare class ContextCaptureManager {
926
954
  addNetworkRequest(request: NetworkRequest): void;
927
955
  private captureConsole;
928
956
  private captureFetch;
957
+ private captureNavigation;
929
958
  private getPerformanceMetrics;
930
959
  private getEnvironmentInfo;
931
960
  }
package/dist/index.d.ts CHANGED
@@ -39,6 +39,8 @@ interface NetworkRequest {
39
39
  duration?: number;
40
40
  timestamp: string;
41
41
  error?: string;
42
+ /** Truncated response body for failed requests (4xx/5xx) */
43
+ responseBody?: string;
42
44
  }
43
45
  /** Enhanced bug context for detailed debugging */
44
46
  interface EnhancedBugContext {
@@ -46,6 +48,8 @@ interface EnhancedBugContext {
46
48
  consoleLogs?: ConsoleLogEntry[];
47
49
  /** Recent network requests (last 20) */
48
50
  networkRequests?: NetworkRequest[];
51
+ /** Auto-captured navigation history (last 20 route changes) */
52
+ navigationHistory?: string[];
49
53
  /** Current Redux/state snapshot (serialized) */
50
54
  stateSnapshot?: Record<string, unknown>;
51
55
  /** Performance metrics */
@@ -602,13 +606,20 @@ declare class BugBearClient {
602
606
  private navigationHistory;
603
607
  constructor(config: BugBearConfig);
604
608
  /**
605
- * Track navigation for context
609
+ * Track navigation for context.
610
+ * Also forwards to contextCapture for auto-tracked navigation.
606
611
  */
607
612
  trackNavigation(route: string): void;
608
613
  /**
609
- * Get current navigation history
614
+ * Get current navigation history.
615
+ * Priority: config callback > manual tracking > auto-captured (pushState/popstate)
610
616
  */
611
617
  getNavigationHistory(): string[];
618
+ /**
619
+ * Get current app context.
620
+ * Uses config.getAppContext() callback if provided, otherwise builds from available data.
621
+ */
622
+ getAppContext(): AppContext;
612
623
  /**
613
624
  * Get current user info from host app or BugBear's own auth
614
625
  */
@@ -892,16 +903,21 @@ declare function createBugBear(config: BugBearConfig): BugBearClient;
892
903
  */
893
904
 
894
905
  /**
895
- * Context capture singleton that captures console logs and network requests
906
+ * Context capture singleton that captures console logs, network requests,
907
+ * and navigation history automatically.
896
908
  */
897
909
  declare class ContextCaptureManager {
898
910
  private consoleLogs;
899
911
  private networkRequests;
912
+ private navigationHistory;
900
913
  private originalConsole;
901
914
  private originalFetch?;
915
+ private originalPushState?;
916
+ private originalReplaceState?;
917
+ private popstateHandler?;
902
918
  private isCapturing;
903
919
  /**
904
- * Start capturing console logs and network requests
920
+ * Start capturing console logs, network requests, and navigation
905
921
  */
906
922
  startCapture(): void;
907
923
  /**
@@ -912,6 +928,18 @@ declare class ContextCaptureManager {
912
928
  * Get captured context for a bug report
913
929
  */
914
930
  getEnhancedContext(): EnhancedBugContext;
931
+ /**
932
+ * Get the auto-captured navigation history
933
+ */
934
+ getNavigationHistory(): string[];
935
+ /**
936
+ * Get the current route (last entry in navigation history, or window.location)
937
+ */
938
+ getCurrentRoute(): string;
939
+ /**
940
+ * Manually track a navigation event (for React Native or custom routing)
941
+ */
942
+ trackNavigation(route: string): void;
915
943
  /**
916
944
  * Clear captured data
917
945
  */
@@ -926,6 +954,7 @@ declare class ContextCaptureManager {
926
954
  addNetworkRequest(request: NetworkRequest): void;
927
955
  private captureConsole;
928
956
  private captureFetch;
957
+ private captureNavigation;
929
958
  private getPerformanceMetrics;
930
959
  private getEnvironmentInfo;
931
960
  }
package/dist/index.js CHANGED
@@ -33,21 +33,25 @@ var import_supabase_js = require("@supabase/supabase-js");
33
33
  // src/capture.ts
34
34
  var MAX_CONSOLE_LOGS = 50;
35
35
  var MAX_NETWORK_REQUESTS = 20;
36
+ var MAX_NAVIGATION_HISTORY = 20;
37
+ var MAX_RESPONSE_BODY_LENGTH = 500;
36
38
  var ContextCaptureManager = class {
37
39
  constructor() {
38
40
  this.consoleLogs = [];
39
41
  this.networkRequests = [];
42
+ this.navigationHistory = [];
40
43
  this.originalConsole = {};
41
44
  this.isCapturing = false;
42
45
  }
43
46
  /**
44
- * Start capturing console logs and network requests
47
+ * Start capturing console logs, network requests, and navigation
45
48
  */
46
49
  startCapture() {
47
50
  if (this.isCapturing) return;
48
51
  this.isCapturing = true;
49
52
  this.captureConsole();
50
53
  this.captureFetch();
54
+ this.captureNavigation();
51
55
  }
52
56
  /**
53
57
  * Stop capturing and restore original functions
@@ -62,6 +66,17 @@ var ContextCaptureManager = class {
62
66
  if (this.originalFetch && typeof window !== "undefined") {
63
67
  window.fetch = this.originalFetch;
64
68
  }
69
+ if (typeof window !== "undefined" && typeof history !== "undefined") {
70
+ if (this.originalPushState) {
71
+ history.pushState = this.originalPushState;
72
+ }
73
+ if (this.originalReplaceState) {
74
+ history.replaceState = this.originalReplaceState;
75
+ }
76
+ if (this.popstateHandler) {
77
+ window.removeEventListener("popstate", this.popstateHandler);
78
+ }
79
+ }
65
80
  }
66
81
  /**
67
82
  * Get captured context for a bug report
@@ -70,16 +85,47 @@ var ContextCaptureManager = class {
70
85
  return {
71
86
  consoleLogs: [...this.consoleLogs],
72
87
  networkRequests: [...this.networkRequests],
88
+ navigationHistory: [...this.navigationHistory],
73
89
  performanceMetrics: this.getPerformanceMetrics(),
74
90
  environment: this.getEnvironmentInfo()
75
91
  };
76
92
  }
93
+ /**
94
+ * Get the auto-captured navigation history
95
+ */
96
+ getNavigationHistory() {
97
+ return [...this.navigationHistory];
98
+ }
99
+ /**
100
+ * Get the current route (last entry in navigation history, or window.location)
101
+ */
102
+ getCurrentRoute() {
103
+ if (this.navigationHistory.length > 0) {
104
+ return this.navigationHistory[this.navigationHistory.length - 1];
105
+ }
106
+ if (typeof window !== "undefined") {
107
+ return window.location.pathname;
108
+ }
109
+ return "unknown";
110
+ }
111
+ /**
112
+ * Manually track a navigation event (for React Native or custom routing)
113
+ */
114
+ trackNavigation(route) {
115
+ const last = this.navigationHistory[this.navigationHistory.length - 1];
116
+ if (route === last) return;
117
+ this.navigationHistory.push(route);
118
+ if (this.navigationHistory.length > MAX_NAVIGATION_HISTORY) {
119
+ this.navigationHistory.shift();
120
+ }
121
+ }
77
122
  /**
78
123
  * Clear captured data
79
124
  */
80
125
  clear() {
81
126
  this.consoleLogs = [];
82
127
  this.networkRequests = [];
128
+ this.navigationHistory = [];
83
129
  }
84
130
  /**
85
131
  * Add a log entry manually (for custom logging)
@@ -136,14 +182,25 @@ var ContextCaptureManager = class {
136
182
  const method = init?.method || "GET";
137
183
  try {
138
184
  const response = await self.originalFetch.call(window, input, init);
139
- self.addNetworkRequest({
185
+ const requestEntry = {
140
186
  method,
141
187
  url: url.slice(0, 200),
142
188
  // Limit URL length
143
189
  status: response.status,
144
190
  duration: Date.now() - startTime,
145
191
  timestamp: (/* @__PURE__ */ new Date()).toISOString()
146
- });
192
+ };
193
+ if (response.status >= 400) {
194
+ try {
195
+ const cloned = response.clone();
196
+ const body = await cloned.text();
197
+ if (body) {
198
+ requestEntry.responseBody = body.slice(0, MAX_RESPONSE_BODY_LENGTH);
199
+ }
200
+ } catch {
201
+ }
202
+ }
203
+ self.addNetworkRequest(requestEntry);
147
204
  return response;
148
205
  } catch (error) {
149
206
  self.addNetworkRequest({
@@ -157,6 +214,25 @@ var ContextCaptureManager = class {
157
214
  }
158
215
  };
159
216
  }
217
+ captureNavigation() {
218
+ if (typeof window === "undefined" || typeof history === "undefined") return;
219
+ this.trackNavigation(window.location.pathname);
220
+ const self = this;
221
+ this.originalPushState = history.pushState;
222
+ history.pushState = function(...args) {
223
+ self.originalPushState.apply(history, args);
224
+ self.trackNavigation(window.location.pathname);
225
+ };
226
+ this.originalReplaceState = history.replaceState;
227
+ history.replaceState = function(...args) {
228
+ self.originalReplaceState.apply(history, args);
229
+ self.trackNavigation(window.location.pathname);
230
+ };
231
+ this.popstateHandler = () => {
232
+ self.trackNavigation(window.location.pathname);
233
+ };
234
+ window.addEventListener("popstate", this.popstateHandler);
235
+ }
160
236
  getPerformanceMetrics() {
161
237
  if (typeof window === "undefined" || typeof performance === "undefined") return void 0;
162
238
  const metrics = {};
@@ -218,22 +294,40 @@ var BugBearClient = class {
218
294
  );
219
295
  }
220
296
  /**
221
- * Track navigation for context
297
+ * Track navigation for context.
298
+ * Also forwards to contextCapture for auto-tracked navigation.
222
299
  */
223
300
  trackNavigation(route) {
224
301
  this.navigationHistory.push(route);
225
302
  if (this.navigationHistory.length > 10) {
226
303
  this.navigationHistory.shift();
227
304
  }
305
+ contextCapture.trackNavigation(route);
228
306
  }
229
307
  /**
230
- * Get current navigation history
308
+ * Get current navigation history.
309
+ * Priority: config callback > manual tracking > auto-captured (pushState/popstate)
231
310
  */
232
311
  getNavigationHistory() {
233
312
  if (this.config.getNavigationHistory) {
234
313
  return this.config.getNavigationHistory();
235
314
  }
236
- return [...this.navigationHistory];
315
+ if (this.navigationHistory.length > 0) {
316
+ return [...this.navigationHistory];
317
+ }
318
+ return contextCapture.getNavigationHistory();
319
+ }
320
+ /**
321
+ * Get current app context.
322
+ * Uses config.getAppContext() callback if provided, otherwise builds from available data.
323
+ */
324
+ getAppContext() {
325
+ if (this.config.getAppContext) {
326
+ return this.config.getAppContext();
327
+ }
328
+ return {
329
+ currentRoute: contextCapture.getCurrentRoute()
330
+ };
237
331
  }
238
332
  /**
239
333
  * Get current user info from host app or BugBear's own auth
package/dist/index.mjs CHANGED
@@ -4,21 +4,25 @@ import { createClient } from "@supabase/supabase-js";
4
4
  // src/capture.ts
5
5
  var MAX_CONSOLE_LOGS = 50;
6
6
  var MAX_NETWORK_REQUESTS = 20;
7
+ var MAX_NAVIGATION_HISTORY = 20;
8
+ var MAX_RESPONSE_BODY_LENGTH = 500;
7
9
  var ContextCaptureManager = class {
8
10
  constructor() {
9
11
  this.consoleLogs = [];
10
12
  this.networkRequests = [];
13
+ this.navigationHistory = [];
11
14
  this.originalConsole = {};
12
15
  this.isCapturing = false;
13
16
  }
14
17
  /**
15
- * Start capturing console logs and network requests
18
+ * Start capturing console logs, network requests, and navigation
16
19
  */
17
20
  startCapture() {
18
21
  if (this.isCapturing) return;
19
22
  this.isCapturing = true;
20
23
  this.captureConsole();
21
24
  this.captureFetch();
25
+ this.captureNavigation();
22
26
  }
23
27
  /**
24
28
  * Stop capturing and restore original functions
@@ -33,6 +37,17 @@ var ContextCaptureManager = class {
33
37
  if (this.originalFetch && typeof window !== "undefined") {
34
38
  window.fetch = this.originalFetch;
35
39
  }
40
+ if (typeof window !== "undefined" && typeof history !== "undefined") {
41
+ if (this.originalPushState) {
42
+ history.pushState = this.originalPushState;
43
+ }
44
+ if (this.originalReplaceState) {
45
+ history.replaceState = this.originalReplaceState;
46
+ }
47
+ if (this.popstateHandler) {
48
+ window.removeEventListener("popstate", this.popstateHandler);
49
+ }
50
+ }
36
51
  }
37
52
  /**
38
53
  * Get captured context for a bug report
@@ -41,16 +56,47 @@ var ContextCaptureManager = class {
41
56
  return {
42
57
  consoleLogs: [...this.consoleLogs],
43
58
  networkRequests: [...this.networkRequests],
59
+ navigationHistory: [...this.navigationHistory],
44
60
  performanceMetrics: this.getPerformanceMetrics(),
45
61
  environment: this.getEnvironmentInfo()
46
62
  };
47
63
  }
64
+ /**
65
+ * Get the auto-captured navigation history
66
+ */
67
+ getNavigationHistory() {
68
+ return [...this.navigationHistory];
69
+ }
70
+ /**
71
+ * Get the current route (last entry in navigation history, or window.location)
72
+ */
73
+ getCurrentRoute() {
74
+ if (this.navigationHistory.length > 0) {
75
+ return this.navigationHistory[this.navigationHistory.length - 1];
76
+ }
77
+ if (typeof window !== "undefined") {
78
+ return window.location.pathname;
79
+ }
80
+ return "unknown";
81
+ }
82
+ /**
83
+ * Manually track a navigation event (for React Native or custom routing)
84
+ */
85
+ trackNavigation(route) {
86
+ const last = this.navigationHistory[this.navigationHistory.length - 1];
87
+ if (route === last) return;
88
+ this.navigationHistory.push(route);
89
+ if (this.navigationHistory.length > MAX_NAVIGATION_HISTORY) {
90
+ this.navigationHistory.shift();
91
+ }
92
+ }
48
93
  /**
49
94
  * Clear captured data
50
95
  */
51
96
  clear() {
52
97
  this.consoleLogs = [];
53
98
  this.networkRequests = [];
99
+ this.navigationHistory = [];
54
100
  }
55
101
  /**
56
102
  * Add a log entry manually (for custom logging)
@@ -107,14 +153,25 @@ var ContextCaptureManager = class {
107
153
  const method = init?.method || "GET";
108
154
  try {
109
155
  const response = await self.originalFetch.call(window, input, init);
110
- self.addNetworkRequest({
156
+ const requestEntry = {
111
157
  method,
112
158
  url: url.slice(0, 200),
113
159
  // Limit URL length
114
160
  status: response.status,
115
161
  duration: Date.now() - startTime,
116
162
  timestamp: (/* @__PURE__ */ new Date()).toISOString()
117
- });
163
+ };
164
+ if (response.status >= 400) {
165
+ try {
166
+ const cloned = response.clone();
167
+ const body = await cloned.text();
168
+ if (body) {
169
+ requestEntry.responseBody = body.slice(0, MAX_RESPONSE_BODY_LENGTH);
170
+ }
171
+ } catch {
172
+ }
173
+ }
174
+ self.addNetworkRequest(requestEntry);
118
175
  return response;
119
176
  } catch (error) {
120
177
  self.addNetworkRequest({
@@ -128,6 +185,25 @@ var ContextCaptureManager = class {
128
185
  }
129
186
  };
130
187
  }
188
+ captureNavigation() {
189
+ if (typeof window === "undefined" || typeof history === "undefined") return;
190
+ this.trackNavigation(window.location.pathname);
191
+ const self = this;
192
+ this.originalPushState = history.pushState;
193
+ history.pushState = function(...args) {
194
+ self.originalPushState.apply(history, args);
195
+ self.trackNavigation(window.location.pathname);
196
+ };
197
+ this.originalReplaceState = history.replaceState;
198
+ history.replaceState = function(...args) {
199
+ self.originalReplaceState.apply(history, args);
200
+ self.trackNavigation(window.location.pathname);
201
+ };
202
+ this.popstateHandler = () => {
203
+ self.trackNavigation(window.location.pathname);
204
+ };
205
+ window.addEventListener("popstate", this.popstateHandler);
206
+ }
131
207
  getPerformanceMetrics() {
132
208
  if (typeof window === "undefined" || typeof performance === "undefined") return void 0;
133
209
  const metrics = {};
@@ -189,22 +265,40 @@ var BugBearClient = class {
189
265
  );
190
266
  }
191
267
  /**
192
- * Track navigation for context
268
+ * Track navigation for context.
269
+ * Also forwards to contextCapture for auto-tracked navigation.
193
270
  */
194
271
  trackNavigation(route) {
195
272
  this.navigationHistory.push(route);
196
273
  if (this.navigationHistory.length > 10) {
197
274
  this.navigationHistory.shift();
198
275
  }
276
+ contextCapture.trackNavigation(route);
199
277
  }
200
278
  /**
201
- * Get current navigation history
279
+ * Get current navigation history.
280
+ * Priority: config callback > manual tracking > auto-captured (pushState/popstate)
202
281
  */
203
282
  getNavigationHistory() {
204
283
  if (this.config.getNavigationHistory) {
205
284
  return this.config.getNavigationHistory();
206
285
  }
207
- return [...this.navigationHistory];
286
+ if (this.navigationHistory.length > 0) {
287
+ return [...this.navigationHistory];
288
+ }
289
+ return contextCapture.getNavigationHistory();
290
+ }
291
+ /**
292
+ * Get current app context.
293
+ * Uses config.getAppContext() callback if provided, otherwise builds from available data.
294
+ */
295
+ getAppContext() {
296
+ if (this.config.getAppContext) {
297
+ return this.config.getAppContext();
298
+ }
299
+ return {
300
+ currentRoute: contextCapture.getCurrentRoute()
301
+ };
208
302
  }
209
303
  /**
210
304
  * Get current user info from host app or BugBear's own auth
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@bbearai/core",
3
- "version": "0.2.11",
3
+ "version": "0.2.12",
4
4
  "description": "Core utilities and types for BugBear QA platform",
5
5
  "main": "./dist/index.js",
6
6
  "module": "./dist/index.mjs",