react-native-qalink 0.1.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.
Files changed (42) hide show
  1. package/README.md +342 -0
  2. package/dist/core/classifier.d.ts +9 -0
  3. package/dist/core/classifier.d.ts.map +1 -0
  4. package/dist/core/classifier.js +51 -0
  5. package/dist/core/classifier.js.map +1 -0
  6. package/dist/core/session.d.ts +8 -0
  7. package/dist/core/session.d.ts.map +1 -0
  8. package/dist/core/session.js +60 -0
  9. package/dist/core/session.js.map +1 -0
  10. package/dist/index.d.ts +58 -0
  11. package/dist/index.d.ts.map +1 -0
  12. package/dist/index.js +171 -0
  13. package/dist/index.js.map +1 -0
  14. package/dist/interceptors/axios.d.ts +4 -0
  15. package/dist/interceptors/axios.d.ts.map +1 -0
  16. package/dist/interceptors/axios.js +78 -0
  17. package/dist/interceptors/axios.js.map +1 -0
  18. package/dist/interceptors/console.d.ts +4 -0
  19. package/dist/interceptors/console.d.ts.map +1 -0
  20. package/dist/interceptors/console.js +159 -0
  21. package/dist/interceptors/console.js.map +1 -0
  22. package/dist/interceptors/errors.d.ts +4 -0
  23. package/dist/interceptors/errors.d.ts.map +1 -0
  24. package/dist/interceptors/errors.js +49 -0
  25. package/dist/interceptors/errors.js.map +1 -0
  26. package/dist/interceptors/fetch.d.ts +4 -0
  27. package/dist/interceptors/fetch.d.ts.map +1 -0
  28. package/dist/interceptors/fetch.js +83 -0
  29. package/dist/interceptors/fetch.js.map +1 -0
  30. package/dist/interceptors/runtime.d.ts +4 -0
  31. package/dist/interceptors/runtime.d.ts.map +1 -0
  32. package/dist/interceptors/runtime.js +141 -0
  33. package/dist/interceptors/runtime.js.map +1 -0
  34. package/dist/transport/websocket.d.ts +23 -0
  35. package/dist/transport/websocket.d.ts.map +1 -0
  36. package/dist/transport/websocket.js +104 -0
  37. package/dist/transport/websocket.js.map +1 -0
  38. package/dist/types/index.d.ts +139 -0
  39. package/dist/types/index.d.ts.map +1 -0
  40. package/dist/types/index.js +3 -0
  41. package/dist/types/index.js.map +1 -0
  42. package/package.json +36 -0
package/dist/index.js ADDED
@@ -0,0 +1,171 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __exportStar = (this && this.__exportStar) || function(m, exports) {
14
+ for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
15
+ };
16
+ Object.defineProperty(exports, "__esModule", { value: true });
17
+ exports.getSourceLabel = exports.QALink = void 0;
18
+ const websocket_1 = require("./transport/websocket");
19
+ const axios_1 = require("./interceptors/axios");
20
+ const fetch_1 = require("./interceptors/fetch");
21
+ const errors_1 = require("./interceptors/errors");
22
+ const console_1 = require("./interceptors/console");
23
+ const runtime_1 = require("./interceptors/runtime");
24
+ const session_1 = require("./core/session");
25
+ class QALinkSDK {
26
+ constructor() {
27
+ this.transport = null;
28
+ this.config = null;
29
+ this.cleanups = [];
30
+ this.initialized = false;
31
+ this.currentScreen = 'unknown';
32
+ }
33
+ /**
34
+ * Inicializa el SDK. Llamar al inicio de la app, antes de cualquier request.
35
+ *
36
+ * @example
37
+ * QALink.init({
38
+ * serverUrl: 'ws://192.168.1.100:3000',
39
+ * appVersion: '1.2.3',
40
+ * captureRuntimeErrors: true,
41
+ * console: {
42
+ * captureLogs: true,
43
+ * captureWarnings: true,
44
+ * captureErrors: true,
45
+ * ignorePatterns: ['[react-query]'],
46
+ * },
47
+ * });
48
+ */
49
+ async init(config) {
50
+ var _a;
51
+ if (this.initialized) {
52
+ console.warn('[QALink] Already initialized. Call destroy() first.');
53
+ return;
54
+ }
55
+ if (config.enabled === false)
56
+ return;
57
+ this.config = Object.assign(Object.assign({ enabled: true, logNetworkBodies: false, sensitiveHeaders: [], sensitiveUrlPatterns: [], captureRuntimeErrors: true, console: {
58
+ captureLogs: true,
59
+ captureWarnings: true,
60
+ captureErrors: true,
61
+ ignorePatterns: [],
62
+ includePatterns: [],
63
+ }, debug: false }, config), {
64
+ // Merge profundo de console config
65
+ console: Object.assign({ captureLogs: true, captureWarnings: true, captureErrors: true, ignorePatterns: [], includePatterns: [] }, ((_a = config.console) !== null && _a !== void 0 ? _a : {})) });
66
+ // 1. WebSocket
67
+ this.transport = new websocket_1.WebSocketTransport(this.config.serverUrl, this.config.debug);
68
+ this.transport.connect();
69
+ // 2. Evento de inicio de sesión
70
+ const deviceInfo = await (0, session_1.getDeviceInfo)(config.appVersion);
71
+ const sessionEvent = {
72
+ id: (0, session_1.generateId)(),
73
+ type: 'session_start',
74
+ sessionId: (0, session_1.getSessionId)(),
75
+ timestamp: Date.now(),
76
+ deviceInfo,
77
+ appVersion: config.appVersion,
78
+ };
79
+ this.transport.send(sessionEvent);
80
+ const getScreen = () => this.currentScreen;
81
+ // 3. Interceptor de fetch nativo
82
+ this.cleanups.push((0, fetch_1.setupFetchInterceptor)(this.transport, this.config));
83
+ // 4. Interceptor de consola (console.log/warn/error + Metro logs)
84
+ this.cleanups.push((0, console_1.setupConsoleInterceptor)(this.transport, this.config, getScreen));
85
+ // 5. Handler de errores del runtime de RN (pantalla roja, yellow box, promises)
86
+ if (this.config.captureRuntimeErrors) {
87
+ this.cleanups.push((0, runtime_1.setupRuntimeErrorHandler)(this.transport, this.config, getScreen));
88
+ }
89
+ // 6. Handler legacy de errores JS (fallback para versiones viejas de RN)
90
+ this.cleanups.push((0, errors_1.setupErrorHandlers)(this.transport, this.config));
91
+ this.initialized = true;
92
+ this.log('SDK initialized ✅', { sessionId: (0, session_1.getSessionId)() });
93
+ }
94
+ /**
95
+ * Registra interceptor para una instancia específica de Axios.
96
+ *
97
+ * @example
98
+ * import axios from 'axios';
99
+ * QALink.interceptAxios(axios);
100
+ *
101
+ * // También con instancias custom:
102
+ * const api = axios.create({ baseURL: 'https://api.miapp.com' });
103
+ * QALink.interceptAxios(api);
104
+ */
105
+ interceptAxios(axiosInstance) {
106
+ if (!this.transport || !this.config) {
107
+ console.warn('[QALink] Call init() before interceptAxios()');
108
+ return;
109
+ }
110
+ this.cleanups.push((0, axios_1.setupAxiosInterceptor)(axiosInstance, this.transport, this.config));
111
+ this.log('Axios interceptor installed ✅');
112
+ }
113
+ /**
114
+ * Registra una acción del usuario (breadcrumb).
115
+ *
116
+ * @example
117
+ * QALink.addBreadcrumb('TAP → Confirmar Compra', { total: 150 });
118
+ */
119
+ addBreadcrumb(action, data) {
120
+ var _a, _b;
121
+ if (!this.transport || !this.initialized)
122
+ return;
123
+ const event = {
124
+ id: (0, session_1.generateId)(),
125
+ type: 'breadcrumb',
126
+ action,
127
+ screen: this.currentScreen,
128
+ data,
129
+ timestamp: Date.now(),
130
+ sessionId: (0, session_1.getSessionId)(),
131
+ };
132
+ this.transport.send(event);
133
+ (_b = (_a = this.config) === null || _a === void 0 ? void 0 : _a.onEvent) === null || _b === void 0 ? void 0 : _b.call(_a, event);
134
+ }
135
+ /**
136
+ * Registra la pantalla actual. Llamar en cada cambio de navegación.
137
+ * Genera automáticamente un breadcrumb de navegación.
138
+ */
139
+ setScreen(screenName) {
140
+ if (!this.initialized)
141
+ return;
142
+ this.currentScreen = screenName;
143
+ this.addBreadcrumb(`NAVIGATE → ${screenName}`);
144
+ }
145
+ /** Estado actual de la conexión WebSocket */
146
+ getStatus() {
147
+ var _a, _b;
148
+ return (_b = (_a = this.transport) === null || _a === void 0 ? void 0 : _a.getStatus()) !== null && _b !== void 0 ? _b : 'not initialized';
149
+ }
150
+ /** Limpia todos los interceptores y desconecta. Útil en tests. */
151
+ destroy() {
152
+ var _a;
153
+ this.cleanups.forEach(fn => fn());
154
+ this.cleanups = [];
155
+ (_a = this.transport) === null || _a === void 0 ? void 0 : _a.disconnect();
156
+ this.transport = null;
157
+ this.config = null;
158
+ this.initialized = false;
159
+ }
160
+ log(...args) {
161
+ var _a;
162
+ if ((_a = this.config) === null || _a === void 0 ? void 0 : _a.debug) {
163
+ console.log('[QALink]', ...args);
164
+ }
165
+ }
166
+ }
167
+ exports.QALink = new QALinkSDK();
168
+ __exportStar(require("./types"), exports);
169
+ var classifier_1 = require("./core/classifier");
170
+ Object.defineProperty(exports, "getSourceLabel", { enumerable: true, get: function () { return classifier_1.getSourceLabel; } });
171
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;AACA,qDAA2D;AAC3D,gDAA6D;AAC7D,gDAA6D;AAC7D,kDAA2D;AAC3D,oDAAiE;AACjE,oDAAkE;AAClE,4CAAyE;AAEzE,MAAM,SAAS;IAAf;QACU,cAAS,GAA8B,IAAI,CAAC;QAC5C,WAAM,GAAwB,IAAI,CAAC;QACnC,aAAQ,GAAsB,EAAE,CAAC;QACjC,gBAAW,GAAG,KAAK,CAAC;QACpB,kBAAa,GAAG,SAAS,CAAC;IAqKpC,CAAC;IAnKC;;;;;;;;;;;;;;;OAeG;IACH,KAAK,CAAC,IAAI,CAAC,MAAoB;;QAC7B,IAAI,IAAI,CAAC,WAAW,EAAE,CAAC;YACrB,OAAO,CAAC,IAAI,CAAC,qDAAqD,CAAC,CAAC;YACpE,OAAO;QACT,CAAC;QAED,IAAI,MAAM,CAAC,OAAO,KAAK,KAAK;YAAE,OAAO;QAErC,IAAI,CAAC,MAAM,iCACT,OAAO,EAAE,IAAI,EACb,gBAAgB,EAAE,KAAK,EACvB,gBAAgB,EAAE,EAAE,EACpB,oBAAoB,EAAE,EAAE,EACxB,oBAAoB,EAAE,IAAI,EAC1B,OAAO,EAAE;gBACP,WAAW,EAAE,IAAI;gBACjB,eAAe,EAAE,IAAI;gBACrB,aAAa,EAAE,IAAI;gBACnB,cAAc,EAAE,EAAE;gBAClB,eAAe,EAAE,EAAE;aACpB,EACD,KAAK,EAAE,KAAK,IACT,MAAM;YACT,mCAAmC;YACnC,OAAO,kBACL,WAAW,EAAE,IAAI,EACjB,eAAe,EAAE,IAAI,EACrB,aAAa,EAAE,IAAI,EACnB,cAAc,EAAE,EAAE,EAClB,eAAe,EAAE,EAAE,IAChB,CAAC,MAAA,MAAM,CAAC,OAAO,mCAAI,EAAE,CAAC,IAE5B,CAAC;QAEF,eAAe;QACf,IAAI,CAAC,SAAS,GAAG,IAAI,8BAAkB,CAAC,IAAI,CAAC,MAAM,CAAC,SAAS,EAAE,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;QAClF,IAAI,CAAC,SAAS,CAAC,OAAO,EAAE,CAAC;QAEzB,gCAAgC;QAChC,MAAM,UAAU,GAAG,MAAM,IAAA,uBAAa,EAAC,MAAM,CAAC,UAAU,CAAC,CAAC;QAC1D,MAAM,YAAY,GAAsB;YACtC,EAAE,EAAE,IAAA,oBAAU,GAAE;YAChB,IAAI,EAAE,eAAe;YACrB,SAAS,EAAE,IAAA,sBAAY,GAAE;YACzB,SAAS,EAAE,IAAI,CAAC,GAAG,EAAE;YACrB,UAAU;YACV,UAAU,EAAE,MAAM,CAAC,UAAU;SAC9B,CAAC;QACF,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,YAAY,CAAC,CAAC;QAElC,MAAM,SAAS,GAAG,GAAG,EAAE,CAAC,IAAI,CAAC,aAAa,CAAC;QAE3C,iCAAiC;QACjC,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAA,6BAAqB,EAAC,IAAI,CAAC,SAAS,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC;QAEvE,kEAAkE;QAClE,IAAI,CAAC,QAAQ,CAAC,IAAI,CAChB,IAAA,iCAAuB,EAAC,IAAI,CAAC,SAAS,EAAE,IAAI,CAAC,MAAM,EAAE,SAAS,CAAC,CAChE,CAAC;QAEF,gFAAgF;QAChF,IAAI,IAAI,CAAC,MAAM,CAAC,oBAAoB,EAAE,CAAC;YACrC,IAAI,CAAC,QAAQ,CAAC,IAAI,CAChB,IAAA,kCAAwB,EAAC,IAAI,CAAC,SAAS,EAAE,IAAI,CAAC,MAAM,EAAE,SAAS,CAAC,CACjE,CAAC;QACJ,CAAC;QAED,yEAAyE;QACzE,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAA,2BAAkB,EAAC,IAAI,CAAC,SAAS,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC;QAEpE,IAAI,CAAC,WAAW,GAAG,IAAI,CAAC;QACxB,IAAI,CAAC,GAAG,CAAC,mBAAmB,EAAE,EAAE,SAAS,EAAE,IAAA,sBAAY,GAAE,EAAE,CAAC,CAAC;IAC/D,CAAC;IAED;;;;;;;;;;OAUG;IACH,cAAc,CAAC,aAAkB;QAC/B,IAAI,CAAC,IAAI,CAAC,SAAS,IAAI,CAAC,IAAI,CAAC,MAAM,EAAE,CAAC;YACpC,OAAO,CAAC,IAAI,CAAC,8CAA8C,CAAC,CAAC;YAC7D,OAAO;QACT,CAAC;QACD,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAA,6BAAqB,EAAC,aAAa,EAAE,IAAI,CAAC,SAAS,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC;QACtF,IAAI,CAAC,GAAG,CAAC,+BAA+B,CAAC,CAAC;IAC5C,CAAC;IAED;;;;;OAKG;IACH,aAAa,CAAC,MAAc,EAAE,IAA8B;;QAC1D,IAAI,CAAC,IAAI,CAAC,SAAS,IAAI,CAAC,IAAI,CAAC,WAAW;YAAE,OAAO;QAEjD,MAAM,KAAK,GAAoB;YAC7B,EAAE,EAAE,IAAA,oBAAU,GAAE;YAChB,IAAI,EAAE,YAAY;YAClB,MAAM;YACN,MAAM,EAAE,IAAI,CAAC,aAAa;YAC1B,IAAI;YACJ,SAAS,EAAE,IAAI,CAAC,GAAG,EAAE;YACrB,SAAS,EAAE,IAAA,sBAAY,GAAE;SAC1B,CAAC;QAEF,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QAC3B,MAAA,MAAA,IAAI,CAAC,MAAM,0CAAE,OAAO,mDAAG,KAAK,CAAC,CAAC;IAChC,CAAC;IAED;;;OAGG;IACH,SAAS,CAAC,UAAkB;QAC1B,IAAI,CAAC,IAAI,CAAC,WAAW;YAAE,OAAO;QAC9B,IAAI,CAAC,aAAa,GAAG,UAAU,CAAC;QAChC,IAAI,CAAC,aAAa,CAAC,cAAc,UAAU,EAAE,CAAC,CAAC;IACjD,CAAC;IAED,6CAA6C;IAC7C,SAAS;;QACP,OAAO,MAAA,MAAA,IAAI,CAAC,SAAS,0CAAE,SAAS,EAAE,mCAAI,iBAAiB,CAAC;IAC1D,CAAC;IAED,kEAAkE;IAClE,OAAO;;QACL,IAAI,CAAC,QAAQ,CAAC,OAAO,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC;QAClC,IAAI,CAAC,QAAQ,GAAG,EAAE,CAAC;QACnB,MAAA,IAAI,CAAC,SAAS,0CAAE,UAAU,EAAE,CAAC;QAC7B,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC;QACtB,IAAI,CAAC,MAAM,GAAG,IAAI,CAAC;QACnB,IAAI,CAAC,WAAW,GAAG,KAAK,CAAC;IAC3B,CAAC;IAEO,GAAG,CAAC,GAAG,IAAe;;QAC5B,IAAI,MAAA,IAAI,CAAC,MAAM,0CAAE,KAAK,EAAE,CAAC;YACvB,OAAO,CAAC,GAAG,CAAC,UAAU,EAAE,GAAG,IAAI,CAAC,CAAC;QACnC,CAAC;IACH,CAAC;CACF;AAEY,QAAA,MAAM,GAAG,IAAI,SAAS,EAAE,CAAC;AAEtC,0CAAwB;AACxB,gDAAmD;AAA1C,4GAAA,cAAc,OAAA"}
@@ -0,0 +1,4 @@
1
+ import { QALinkConfig } from '../types';
2
+ import { WebSocketTransport } from '../transport/websocket';
3
+ export declare function setupAxiosInterceptor(axiosInstance: any, transport: WebSocketTransport, config: QALinkConfig): () => void;
4
+ //# sourceMappingURL=axios.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"axios.d.ts","sourceRoot":"","sources":["../../src/interceptors/axios.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAgB,MAAM,UAAU,CAAC;AAGtD,OAAO,EAAE,kBAAkB,EAAE,MAAM,wBAAwB,CAAC;AAE5D,wBAAgB,qBAAqB,CACnC,aAAa,EAAE,GAAG,EAClB,SAAS,EAAE,kBAAkB,EAC7B,MAAM,EAAE,YAAY,GACnB,MAAM,IAAI,CAuEZ"}
@@ -0,0 +1,78 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.setupAxiosInterceptor = setupAxiosInterceptor;
4
+ const classifier_1 = require("../core/classifier");
5
+ const session_1 = require("../core/session");
6
+ function setupAxiosInterceptor(axiosInstance, transport, config) {
7
+ const startTimes = new Map();
8
+ const requestInterceptorId = axiosInstance.interceptors.request.use((axiosConfig) => {
9
+ const requestId = (0, session_1.generateId)();
10
+ axiosConfig._qalinkId = requestId;
11
+ axiosConfig._qalinkStart = Date.now();
12
+ startTimes.set(requestId, Date.now());
13
+ return axiosConfig;
14
+ }, (error) => Promise.reject(error));
15
+ const responseInterceptorId = axiosInstance.interceptors.response.use((response) => {
16
+ var _a, _b, _c, _d, _e, _f, _g, _h, _j;
17
+ const durationMs = Date.now() - ((_a = response.config._qalinkStart) !== null && _a !== void 0 ? _a : Date.now());
18
+ const statusCode = response.status;
19
+ const event = {
20
+ id: (_b = response.config._qalinkId) !== null && _b !== void 0 ? _b : (0, session_1.generateId)(),
21
+ type: 'network_request',
22
+ method: (_d = (_c = response.config.method) === null || _c === void 0 ? void 0 : _c.toUpperCase()) !== null && _d !== void 0 ? _d : 'UNKNOWN',
23
+ url: buildFullUrl(response.config),
24
+ statusCode,
25
+ requestHeaders: (0, session_1.sanitizeHeaders)((_e = response.config.headers) !== null && _e !== void 0 ? _e : {}, config.sensitiveHeaders),
26
+ requestBody: (0, session_1.sanitizeBody)(response.config.data, (_f = config.logNetworkBodies) !== null && _f !== void 0 ? _f : false),
27
+ responseHeaders: (0, session_1.sanitizeHeaders)((_g = response.headers) !== null && _g !== void 0 ? _g : {}, config.sensitiveHeaders),
28
+ responseBody: (0, session_1.sanitizeBody)(response.data, (_h = config.logNetworkBodies) !== null && _h !== void 0 ? _h : false),
29
+ durationMs,
30
+ timestamp: Date.now(),
31
+ source: (0, classifier_1.classifyErrorSource)(statusCode),
32
+ sessionId: (0, session_1.getSessionId)(),
33
+ };
34
+ transport.send(event);
35
+ (_j = config.onEvent) === null || _j === void 0 ? void 0 : _j.call(config, event);
36
+ return response;
37
+ }, (error) => {
38
+ var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o;
39
+ const axiosConfig = (_a = error.config) !== null && _a !== void 0 ? _a : {};
40
+ const durationMs = Date.now() - ((_b = axiosConfig._qalinkStart) !== null && _b !== void 0 ? _b : Date.now());
41
+ const statusCode = (_c = error.response) === null || _c === void 0 ? void 0 : _c.status;
42
+ const source = (0, classifier_1.classifyErrorSource)(statusCode, error);
43
+ const event = {
44
+ id: (_d = axiosConfig._qalinkId) !== null && _d !== void 0 ? _d : (0, session_1.generateId)(),
45
+ type: 'network_error',
46
+ method: (_f = (_e = axiosConfig.method) === null || _e === void 0 ? void 0 : _e.toUpperCase()) !== null && _f !== void 0 ? _f : 'UNKNOWN',
47
+ url: buildFullUrl(axiosConfig),
48
+ statusCode,
49
+ requestHeaders: (0, session_1.sanitizeHeaders)((_g = axiosConfig.headers) !== null && _g !== void 0 ? _g : {}, config.sensitiveHeaders),
50
+ requestBody: (0, session_1.sanitizeBody)(axiosConfig.data, (_h = config.logNetworkBodies) !== null && _h !== void 0 ? _h : false),
51
+ responseHeaders: (0, session_1.sanitizeHeaders)((_k = (_j = error.response) === null || _j === void 0 ? void 0 : _j.headers) !== null && _k !== void 0 ? _k : {}, config.sensitiveHeaders),
52
+ responseBody: (0, session_1.sanitizeBody)((_l = error.response) === null || _l === void 0 ? void 0 : _l.data, (_m = config.logNetworkBodies) !== null && _m !== void 0 ? _m : false),
53
+ durationMs,
54
+ timestamp: Date.now(),
55
+ source,
56
+ sessionId: (0, session_1.getSessionId)(),
57
+ };
58
+ transport.send(event);
59
+ (_o = config.onEvent) === null || _o === void 0 ? void 0 : _o.call(config, event);
60
+ return Promise.reject(error);
61
+ });
62
+ return () => {
63
+ axiosInstance.interceptors.request.eject(requestInterceptorId);
64
+ axiosInstance.interceptors.response.eject(responseInterceptorId);
65
+ };
66
+ }
67
+ function buildFullUrl(axiosConfig) {
68
+ var _a, _b, _c;
69
+ try {
70
+ const base = (_a = axiosConfig.baseURL) !== null && _a !== void 0 ? _a : '';
71
+ const url = (_b = axiosConfig.url) !== null && _b !== void 0 ? _b : '';
72
+ return base ? `${base.replace(/\/$/, '')}/${url.replace(/^\//, '')}` : url;
73
+ }
74
+ catch (_d) {
75
+ return (_c = axiosConfig.url) !== null && _c !== void 0 ? _c : 'unknown';
76
+ }
77
+ }
78
+ //# sourceMappingURL=axios.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"axios.js","sourceRoot":"","sources":["../../src/interceptors/axios.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,4 @@
1
+ import { QALinkConfig } from '../types';
2
+ import { WebSocketTransport } from '../transport/websocket';
3
+ export declare function setupConsoleInterceptor(transport: WebSocketTransport, config: QALinkConfig, getCurrentScreen: () => string): () => void;
4
+ //# sourceMappingURL=console.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"console.d.ts","sourceRoot":"","sources":["../../src/interceptors/console.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAA8B,MAAM,UAAU,CAAC;AAEpE,OAAO,EAAE,kBAAkB,EAAE,MAAM,wBAAwB,CAAC;AAuG5D,wBAAgB,uBAAuB,CACrC,SAAS,EAAE,kBAAkB,EAC7B,MAAM,EAAE,YAAY,EACpB,gBAAgB,EAAE,MAAM,MAAM,GAC7B,MAAM,IAAI,CAmEZ"}
@@ -0,0 +1,159 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.setupConsoleInterceptor = setupConsoleInterceptor;
4
+ const session_1 = require("../core/session");
5
+ // Guardamos referencia a los métodos originales ANTES de sobrescribir
6
+ const originalConsole = {
7
+ log: console.log.bind(console),
8
+ warn: console.warn.bind(console),
9
+ error: console.error.bind(console),
10
+ info: console.info.bind(console),
11
+ debug: console.debug.bind(console),
12
+ };
13
+ /**
14
+ * Patrones que identifican logs internos de React Native
15
+ * para clasificarlos correctamente en el dashboard.
16
+ */
17
+ const RN_WARNING_PATTERNS = [
18
+ 'Warning:',
19
+ 'VirtualizedList',
20
+ 'Each child in a list',
21
+ 'componentWillMount',
22
+ 'componentWillReceiveProps',
23
+ 'componentWillUpdate',
24
+ 'findDOMNode',
25
+ 'ReactDOM.render',
26
+ 'key prop',
27
+ 'unique "key"',
28
+ 'Maximum update depth',
29
+ ];
30
+ const RN_ERROR_PATTERNS = [
31
+ 'Invariant Violation',
32
+ 'Text strings must be rendered',
33
+ 'Cannot update a component',
34
+ 'Element type is invalid',
35
+ 'Objects are not valid as a React child',
36
+ 'TypeError',
37
+ 'ReferenceError',
38
+ 'Cannot read property',
39
+ 'Cannot read properties',
40
+ 'is not a function',
41
+ 'undefined is not an object',
42
+ 'null is not an object',
43
+ ];
44
+ const METRO_ERROR_PATTERNS = [
45
+ 'Unable to resolve module',
46
+ 'Module not found',
47
+ 'SyntaxError',
48
+ 'TransformError',
49
+ 'bundling failed',
50
+ 'Metro Bundler',
51
+ 'Error: Metro',
52
+ ];
53
+ const THIRD_PARTY_PATTERNS = [
54
+ '[react-navigation]',
55
+ '[react-query]',
56
+ '[redux]',
57
+ '[mobx]',
58
+ '[zustand]',
59
+ 'Reanimated',
60
+ 'Gesture Handler',
61
+ 'SafeAreaProvider',
62
+ ];
63
+ function classifyConsoleMessage(message) {
64
+ if (METRO_ERROR_PATTERNS.some(p => message.includes(p)))
65
+ return 'rn_error';
66
+ if (RN_ERROR_PATTERNS.some(p => message.includes(p)))
67
+ return 'rn_error';
68
+ if (RN_WARNING_PATTERNS.some(p => message.includes(p)))
69
+ return 'rn_warning';
70
+ if (THIRD_PARTY_PATTERNS.some(p => message.includes(p)))
71
+ return 'third_party';
72
+ return 'user_log';
73
+ }
74
+ function serializeArg(arg) {
75
+ var _a;
76
+ if (arg === null)
77
+ return 'null';
78
+ if (arg === undefined)
79
+ return 'undefined';
80
+ if (typeof arg === 'string')
81
+ return arg;
82
+ if (typeof arg === 'number' || typeof arg === 'boolean')
83
+ return String(arg);
84
+ if (arg instanceof Error)
85
+ return `${arg.name}: ${arg.message}\n${(_a = arg.stack) !== null && _a !== void 0 ? _a : ''}`;
86
+ try {
87
+ return JSON.stringify(arg, null, 2);
88
+ }
89
+ catch (_b) {
90
+ return String(arg);
91
+ }
92
+ }
93
+ function shouldCapture(message, config) {
94
+ var _a;
95
+ if (!config)
96
+ return true;
97
+ // Ignorar si matchea algún patrón de exclusión
98
+ if ((_a = config.ignorePatterns) === null || _a === void 0 ? void 0 : _a.some(p => message.includes(p)))
99
+ return false;
100
+ // Si hay patrones de inclusión, solo capturar si matchea alguno
101
+ if (config.includePatterns && config.includePatterns.length > 0) {
102
+ return config.includePatterns.some(p => message.includes(p));
103
+ }
104
+ return true;
105
+ }
106
+ function setupConsoleInterceptor(transport, config, getCurrentScreen) {
107
+ var _a;
108
+ const consoleConfig = (_a = config.console) !== null && _a !== void 0 ? _a : {};
109
+ const { captureLogs = true, captureWarnings = true, captureErrors = true, } = consoleConfig;
110
+ function intercept(level, eventType, originalFn) {
111
+ return (...args) => {
112
+ var _a;
113
+ // Siempre llamar al original primero — Metro sigue mostrando todo
114
+ originalFn(...args);
115
+ const serializedArgs = args.map(serializeArg);
116
+ const message = serializedArgs.join(' ');
117
+ if (!shouldCapture(message, consoleConfig))
118
+ return;
119
+ // Evitar loop infinito si QALink mismo hace console.log en debug mode
120
+ if (message.startsWith('[QALink]'))
121
+ return;
122
+ const category = classifyConsoleMessage(message);
123
+ const event = {
124
+ id: (0, session_1.generateId)(),
125
+ type: eventType,
126
+ level,
127
+ message,
128
+ args: serializedArgs,
129
+ category,
130
+ timestamp: Date.now(),
131
+ screen: getCurrentScreen(),
132
+ sessionId: (0, session_1.getSessionId)(),
133
+ };
134
+ transport.send(event);
135
+ (_a = config.onEvent) === null || _a === void 0 ? void 0 : _a.call(config, event);
136
+ };
137
+ }
138
+ // Sobrescribir métodos de consola
139
+ if (captureLogs) {
140
+ console.log = intercept('log', 'console_log', originalConsole.log);
141
+ console.info = intercept('info', 'console_log', originalConsole.info);
142
+ console.debug = intercept('debug', 'console_log', originalConsole.debug);
143
+ }
144
+ if (captureWarnings) {
145
+ console.warn = intercept('warn', 'console_warn', originalConsole.warn);
146
+ }
147
+ if (captureErrors) {
148
+ console.error = intercept('error', 'console_error', originalConsole.error);
149
+ }
150
+ // Cleanup: restaurar consola original
151
+ return () => {
152
+ console.log = originalConsole.log;
153
+ console.warn = originalConsole.warn;
154
+ console.error = originalConsole.error;
155
+ console.info = originalConsole.info;
156
+ console.debug = originalConsole.debug;
157
+ };
158
+ }
159
+ //# sourceMappingURL=console.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"console.js","sourceRoot":"","sources":["../../src/interceptors/console.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,4 @@
1
+ import { QALinkConfig } from '../types';
2
+ import { WebSocketTransport } from '../transport/websocket';
3
+ export declare function setupErrorHandlers(transport: WebSocketTransport, config: QALinkConfig): () => void;
4
+ //# sourceMappingURL=errors.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../../src/interceptors/errors.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAgB,MAAM,UAAU,CAAC;AAEtD,OAAO,EAAE,kBAAkB,EAAE,MAAM,wBAAwB,CAAC;AAE5D,wBAAgB,kBAAkB,CAChC,SAAS,EAAE,kBAAkB,EAC7B,MAAM,EAAE,YAAY,GACnB,MAAM,IAAI,CAiDZ"}
@@ -0,0 +1,49 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.setupErrorHandlers = setupErrorHandlers;
4
+ const session_1 = require("../core/session");
5
+ function setupErrorHandlers(transport, config) {
6
+ const cleanups = [];
7
+ const originalErrorHandler = ErrorUtils.getGlobalHandler();
8
+ ErrorUtils.setGlobalHandler((error, isFatal) => {
9
+ var _a, _b;
10
+ const event = {
11
+ id: (0, session_1.generateId)(),
12
+ type: 'js_error',
13
+ message: (_a = error === null || error === void 0 ? void 0 : error.message) !== null && _a !== void 0 ? _a : String(error),
14
+ stack: error === null || error === void 0 ? void 0 : error.stack,
15
+ timestamp: Date.now(),
16
+ source: 'FRONTEND',
17
+ sessionId: (0, session_1.getSessionId)(),
18
+ };
19
+ transport.send(event);
20
+ (_b = config.onEvent) === null || _b === void 0 ? void 0 : _b.call(config, event);
21
+ originalErrorHandler(error, isFatal);
22
+ });
23
+ cleanups.push(() => {
24
+ ErrorUtils.setGlobalHandler(originalErrorHandler);
25
+ });
26
+ const unhandledRejectionHandler = (event) => {
27
+ var _a, _b;
28
+ const error = event === null || event === void 0 ? void 0 : event.reason;
29
+ const jsEvent = {
30
+ id: (0, session_1.generateId)(),
31
+ type: 'js_error',
32
+ message: (_a = error === null || error === void 0 ? void 0 : error.message) !== null && _a !== void 0 ? _a : 'Unhandled Promise Rejection',
33
+ stack: error === null || error === void 0 ? void 0 : error.stack,
34
+ timestamp: Date.now(),
35
+ source: 'FRONTEND',
36
+ sessionId: (0, session_1.getSessionId)(),
37
+ };
38
+ transport.send(jsEvent);
39
+ (_b = config.onEvent) === null || _b === void 0 ? void 0 : _b.call(config, jsEvent);
40
+ };
41
+ if (typeof global !== 'undefined' && global.addEventListener) {
42
+ global.addEventListener('unhandledrejection', unhandledRejectionHandler);
43
+ cleanups.push(() => {
44
+ global.removeEventListener('unhandledrejection', unhandledRejectionHandler);
45
+ });
46
+ }
47
+ return () => cleanups.forEach(fn => fn());
48
+ }
49
+ //# sourceMappingURL=errors.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"errors.js","sourceRoot":"","sources":["../../src/interceptors/errors.ts"],"names":[],"mappings":";;AAIA,gDAoDC;AAvDD,6CAA2D;AAG3D,SAAgB,kBAAkB,CAChC,SAA6B,EAC7B,MAAoB;IAEpB,MAAM,QAAQ,GAAsB,EAAE,CAAC;IAEvC,MAAM,oBAAoB,GAAG,UAAU,CAAC,gBAAgB,EAAE,CAAC;IAE3D,UAAU,CAAC,gBAAgB,CAAC,CAAC,KAAY,EAAE,OAAiB,EAAE,EAAE;;QAC9D,MAAM,KAAK,GAAiB;YAC1B,EAAE,EAAE,IAAA,oBAAU,GAAE;YAChB,IAAI,EAAE,UAAU;YAChB,OAAO,EAAE,MAAA,KAAK,aAAL,KAAK,uBAAL,KAAK,CAAE,OAAO,mCAAI,MAAM,CAAC,KAAK,CAAC;YACxC,KAAK,EAAE,KAAK,aAAL,KAAK,uBAAL,KAAK,CAAE,KAAK;YACnB,SAAS,EAAE,IAAI,CAAC,GAAG,EAAE;YACrB,MAAM,EAAE,UAAU;YAClB,SAAS,EAAE,IAAA,sBAAY,GAAE;SAC1B,CAAC;QAEF,SAAS,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QACtB,MAAA,MAAM,CAAC,OAAO,uDAAG,KAAK,CAAC,CAAC;QACxB,oBAAoB,CAAC,KAAK,EAAE,OAAO,CAAC,CAAC;IACvC,CAAC,CAAC,CAAC;IAEH,QAAQ,CAAC,IAAI,CAAC,GAAG,EAAE;QACjB,UAAU,CAAC,gBAAgB,CAAC,oBAAoB,CAAC,CAAC;IACpD,CAAC,CAAC,CAAC;IAEH,MAAM,yBAAyB,GAAG,CAAC,KAAU,EAAE,EAAE;;QAC/C,MAAM,KAAK,GAAG,KAAK,aAAL,KAAK,uBAAL,KAAK,CAAE,MAAM,CAAC;QAC5B,MAAM,OAAO,GAAiB;YAC5B,EAAE,EAAE,IAAA,oBAAU,GAAE;YAChB,IAAI,EAAE,UAAU;YAChB,OAAO,EAAE,MAAA,KAAK,aAAL,KAAK,uBAAL,KAAK,CAAE,OAAO,mCAAI,6BAA6B;YACxD,KAAK,EAAE,KAAK,aAAL,KAAK,uBAAL,KAAK,CAAE,KAAK;YACnB,SAAS,EAAE,IAAI,CAAC,GAAG,EAAE;YACrB,MAAM,EAAE,UAAU;YAClB,SAAS,EAAE,IAAA,sBAAY,GAAE;SAC1B,CAAC;QAEF,SAAS,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;QACxB,MAAA,MAAM,CAAC,OAAO,uDAAG,OAAO,CAAC,CAAC;IAC5B,CAAC,CAAC;IAEF,IAAI,OAAO,MAAM,KAAK,WAAW,IAAI,MAAM,CAAC,gBAAgB,EAAE,CAAC;QAC7D,MAAM,CAAC,gBAAgB,CAAC,oBAAoB,EAAE,yBAAyB,CAAC,CAAC;QACzE,QAAQ,CAAC,IAAI,CAAC,GAAG,EAAE;YACjB,MAAM,CAAC,mBAAmB,CAAC,oBAAoB,EAAE,yBAAyB,CAAC,CAAC;QAC9E,CAAC,CAAC,CAAC;IACL,CAAC;IAED,OAAO,GAAG,EAAE,CAAC,QAAQ,CAAC,OAAO,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC;AAC5C,CAAC"}
@@ -0,0 +1,4 @@
1
+ import { QALinkConfig } from '../types';
2
+ import { WebSocketTransport } from '../transport/websocket';
3
+ export declare function setupFetchInterceptor(transport: WebSocketTransport, config: QALinkConfig): () => void;
4
+ //# sourceMappingURL=fetch.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"fetch.d.ts","sourceRoot":"","sources":["../../src/interceptors/fetch.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAgB,MAAM,UAAU,CAAC;AAGtD,OAAO,EAAE,kBAAkB,EAAE,MAAM,wBAAwB,CAAC;AAI5D,wBAAgB,qBAAqB,CACnC,SAAS,EAAE,kBAAkB,EAC7B,MAAM,EAAE,YAAY,GACnB,MAAM,IAAI,CA8EZ"}
@@ -0,0 +1,83 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.setupFetchInterceptor = setupFetchInterceptor;
4
+ const classifier_1 = require("../core/classifier");
5
+ const session_1 = require("../core/session");
6
+ const originalFetch = global.fetch;
7
+ function setupFetchInterceptor(transport, config) {
8
+ global.fetch = async (input, init) => {
9
+ var _a, _b, _c, _d, _e, _f, _g, _h;
10
+ const requestId = (0, session_1.generateId)();
11
+ const startTime = Date.now();
12
+ const method = (_b = (_a = init === null || init === void 0 ? void 0 : init.method) === null || _a === void 0 ? void 0 : _a.toUpperCase()) !== null && _b !== void 0 ? _b : 'GET';
13
+ const url = typeof input === 'string' ? input : input instanceof URL ? input.toString() : input.url;
14
+ if (shouldIgnoreUrl(url, (_c = config.sensitiveUrlPatterns) !== null && _c !== void 0 ? _c : [])) {
15
+ return originalFetch(input, init);
16
+ }
17
+ let response;
18
+ let responseBody;
19
+ let statusCode;
20
+ try {
21
+ response = await originalFetch(input, init);
22
+ statusCode = response.status;
23
+ if (config.logNetworkBodies) {
24
+ try {
25
+ const cloned = response.clone();
26
+ responseBody = await cloned.json().catch(() => cloned.text());
27
+ }
28
+ catch (_j) {
29
+ responseBody = '[could not read body]';
30
+ }
31
+ }
32
+ const event = {
33
+ id: requestId,
34
+ type: statusCode >= 400 ? 'network_error' : 'network_request',
35
+ method,
36
+ url,
37
+ statusCode,
38
+ requestHeaders: (0, session_1.sanitizeHeaders)(headersToObject(new Headers(init === null || init === void 0 ? void 0 : init.headers)), config.sensitiveHeaders),
39
+ requestBody: (0, session_1.sanitizeBody)(init === null || init === void 0 ? void 0 : init.body, (_d = config.logNetworkBodies) !== null && _d !== void 0 ? _d : false),
40
+ responseBody: (0, session_1.sanitizeBody)(responseBody, (_e = config.logNetworkBodies) !== null && _e !== void 0 ? _e : false),
41
+ durationMs: Date.now() - startTime,
42
+ timestamp: Date.now(),
43
+ source: (0, classifier_1.classifyErrorSource)(statusCode),
44
+ sessionId: (0, session_1.getSessionId)(),
45
+ };
46
+ transport.send(event);
47
+ (_f = config.onEvent) === null || _f === void 0 ? void 0 : _f.call(config, event);
48
+ return response;
49
+ }
50
+ catch (error) {
51
+ const event = {
52
+ id: requestId,
53
+ type: 'network_error',
54
+ method,
55
+ url,
56
+ statusCode: undefined,
57
+ requestHeaders: (0, session_1.sanitizeHeaders)(headersToObject(new Headers(init === null || init === void 0 ? void 0 : init.headers)), config.sensitiveHeaders),
58
+ requestBody: (0, session_1.sanitizeBody)(init === null || init === void 0 ? void 0 : init.body, (_g = config.logNetworkBodies) !== null && _g !== void 0 ? _g : false),
59
+ durationMs: Date.now() - startTime,
60
+ timestamp: Date.now(),
61
+ source: (0, classifier_1.classifyErrorSource)(undefined, error),
62
+ sessionId: (0, session_1.getSessionId)(),
63
+ };
64
+ transport.send(event);
65
+ (_h = config.onEvent) === null || _h === void 0 ? void 0 : _h.call(config, event);
66
+ throw error;
67
+ }
68
+ };
69
+ return () => {
70
+ global.fetch = originalFetch;
71
+ };
72
+ }
73
+ function headersToObject(headers) {
74
+ const result = {};
75
+ headers.forEach((value, key) => {
76
+ result[key] = value;
77
+ });
78
+ return result;
79
+ }
80
+ function shouldIgnoreUrl(url, patterns) {
81
+ return patterns.some(pattern => url.includes(pattern));
82
+ }
83
+ //# sourceMappingURL=fetch.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"fetch.js","sourceRoot":"","sources":["../../src/interceptors/fetch.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,4 @@
1
+ import { QALinkConfig } from '../types';
2
+ import { WebSocketTransport } from '../transport/websocket';
3
+ export declare function setupRuntimeErrorHandler(transport: WebSocketTransport, config: QALinkConfig, getCurrentScreen: () => string): () => void;
4
+ //# sourceMappingURL=runtime.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"runtime.d.ts","sourceRoot":"","sources":["../../src/interceptors/runtime.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAqB,MAAM,UAAU,CAAC;AAE3D,OAAO,EAAE,kBAAkB,EAAE,MAAM,wBAAwB,CAAC;AAiD5D,wBAAgB,wBAAwB,CACtC,SAAS,EAAE,kBAAkB,EAC7B,MAAM,EAAE,YAAY,EACpB,gBAAgB,EAAE,MAAM,MAAM,GAC7B,MAAM,IAAI,CA2GZ"}