@arms/rum-reactnative 0.1.3-beta.5 → 0.1.4-beta.1

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 (83) hide show
  1. package/README.md +6 -0
  2. package/android/src/main/java/com/rumsdkreactnative/RumSdkReactnativeModule.kt +31 -0
  3. package/docs/ReactNative SDK/351/205/215/347/275/256/345/217/202/350/200/203.md" +25 -0
  4. package/docs/SDK /347/211/210/346/234/254/350/257/264/346/230/216.md" +14 -0
  5. package/ios/RumAppStateRecorder.h +69 -0
  6. package/ios/RumAppStateRecorder.mm +547 -0
  7. package/ios/RumCrashReporter.h +32 -0
  8. package/ios/RumCrashReporter.mm +97 -11
  9. package/ios/RumSdkReactnative.mm +81 -1
  10. package/lib/commonjs/NativeRumSdkReactnative.js +1 -54
  11. package/lib/commonjs/collector/action/index.js +1 -108
  12. package/lib/commonjs/collector/exception/crash.js +1 -148
  13. package/lib/commonjs/collector/exception/index.js +1 -238
  14. package/lib/commonjs/collector/exception/oom.js +1 -0
  15. package/lib/commonjs/collector/index.js +1 -42
  16. package/lib/commonjs/collector/resource/api.js +1 -292
  17. package/lib/commonjs/collector/view/perf.js +1 -79
  18. package/lib/commonjs/collector/view/pv.js +1 -88
  19. package/lib/commonjs/expoConfigPlugin.js +1 -37
  20. package/lib/commonjs/index.js +1 -29
  21. package/lib/commonjs/plugin.js +1 -47
  22. package/lib/commonjs/processor/default-processor.js +1 -27
  23. package/lib/commonjs/processor/session-processor.js +1 -47
  24. package/lib/commonjs/reporter/index.js +1 -148
  25. package/lib/commonjs/reporter/monitor-reporter.js +1 -43
  26. package/lib/commonjs/shell.js +1 -91
  27. package/lib/commonjs/types/client.js +1 -6
  28. package/lib/commonjs/types/crash.js +1 -37
  29. package/lib/commonjs/types/index.js +1 -2
  30. package/lib/commonjs/types/oom.js +1 -0
  31. package/lib/commonjs/utils/action.js +1 -305
  32. package/lib/commonjs/utils/api.js +1 -84
  33. package/lib/commonjs/utils/base.js +1 -95
  34. package/lib/commonjs/utils/crash.js +1 -149
  35. package/lib/commonjs/utils/platform.js +1 -162
  36. package/lib/commonjs/utils/session.js +1 -158
  37. package/lib/commonjs/utils/url.js +1 -59
  38. package/lib/commonjs/utils/view.js +1 -93
  39. package/lib/module/NativeRumSdkReactnative.js +1 -51
  40. package/lib/module/collector/action/index.js +1 -103
  41. package/lib/module/collector/exception/crash.js +1 -143
  42. package/lib/module/collector/exception/index.js +1 -233
  43. package/lib/module/collector/exception/oom.js +1 -0
  44. package/lib/module/collector/index.js +1 -8
  45. package/lib/module/collector/resource/api.js +1 -287
  46. package/lib/module/collector/view/perf.js +1 -79
  47. package/lib/module/collector/view/pv.js +1 -83
  48. package/lib/module/expoConfigPlugin.js +1 -33
  49. package/lib/module/index.js +1 -7
  50. package/lib/module/plugin.js +1 -42
  51. package/lib/module/processor/default-processor.js +1 -22
  52. package/lib/module/processor/session-processor.js +1 -42
  53. package/lib/module/reporter/index.js +1 -144
  54. package/lib/module/reporter/monitor-reporter.js +1 -38
  55. package/lib/module/shell.js +1 -84
  56. package/lib/module/types/client.js +1 -4
  57. package/lib/module/types/crash.js +1 -33
  58. package/lib/module/types/index.js +1 -2
  59. package/lib/module/types/oom.js +1 -0
  60. package/lib/module/utils/action.js +1 -299
  61. package/lib/module/utils/api.js +1 -76
  62. package/lib/module/utils/base.js +1 -90
  63. package/lib/module/utils/crash.js +1 -144
  64. package/lib/module/utils/platform.js +1 -150
  65. package/lib/module/utils/session.js +1 -154
  66. package/lib/module/utils/url.js +1 -54
  67. package/lib/module/utils/view.js +1 -88
  68. package/lib/typescript/commonjs/src/NativeRumSdkReactnative.d.ts +10 -0
  69. package/lib/typescript/commonjs/src/collector/exception/oom.d.ts +34 -0
  70. package/lib/typescript/commonjs/src/collector/index.d.ts +1 -0
  71. package/lib/typescript/commonjs/src/shell.d.ts +1 -1
  72. package/lib/typescript/commonjs/src/types/client.d.ts +27 -0
  73. package/lib/typescript/commonjs/src/types/oom.d.ts +58 -0
  74. package/lib/typescript/commonjs/src/utils/crash.d.ts +13 -0
  75. package/lib/typescript/module/src/NativeRumSdkReactnative.d.ts +10 -0
  76. package/lib/typescript/module/src/collector/exception/oom.d.ts +34 -0
  77. package/lib/typescript/module/src/collector/index.d.ts +1 -0
  78. package/lib/typescript/module/src/shell.d.ts +1 -1
  79. package/lib/typescript/module/src/types/client.d.ts +27 -0
  80. package/lib/typescript/module/src/types/oom.d.ts +58 -0
  81. package/lib/typescript/module/src/utils/crash.d.ts +13 -0
  82. package/package.json +1 -2
  83. package/src/NativeRumSdkReactnative.ts +18 -0
@@ -1,162 +1 @@
1
- "use strict";
2
-
3
- Object.defineProperty(exports, "__esModule", {
4
- value: true
5
- });
6
- exports.appName = exports.VERSION = void 0;
7
- exports.clearStorage = clearStorage;
8
- exports.fixAttrs = void 0;
9
- exports.getAllStorageKeys = getAllStorageKeys;
10
- exports.getStorage = getStorage;
11
- exports.removeStorage = removeStorage;
12
- exports.setStorage = setStorage;
13
- var _rumCore = require("@arms/rum-core");
14
- var _reactNative = require("react-native");
15
- var _NativeRumSdkReactnative = _interopRequireDefault(require("../NativeRumSdkReactnative"));
16
- function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
17
- const _pkg = {"version":"0.1.3-beta.5"};
18
- const VERSION = exports.VERSION = _pkg.version;
19
-
20
- // eslint-disable-next-line @typescript-eslint/no-unused-vars
21
-
22
- const appName = exports.appName = 'react-native';
23
-
24
- /**
25
- * 从 react-native/package.json 获取 RN 运行时版本号,
26
- * 用于 os.container_version。
27
- */
28
- function getReactNativeVersion() {
29
- try {
30
- const pkg = require('react-native/package.json');
31
- return pkg.version ?? '';
32
- } catch {
33
- const info = _reactNative.Platform.constants?.reactNativeVersion;
34
- if (info) {
35
- return `${info.major}.${info.minor}.${info.patch}`;
36
- }
37
- return '';
38
- }
39
- }
40
-
41
- // region Storage
42
-
43
- function getStorage(key) {
44
- return _NativeRumSdkReactnative.default.getItem(key);
45
- }
46
- function setStorage(key, data) {
47
- return _NativeRumSdkReactnative.default.setItem(key, data);
48
- }
49
- function removeStorage(key) {
50
- return _NativeRumSdkReactnative.default.removeItem(key);
51
- }
52
- function clearStorage() {
53
- return _NativeRumSdkReactnative.default.clear();
54
- }
55
- function getAllStorageKeys() {
56
- return _NativeRumSdkReactnative.default.getAllKeys();
57
- }
58
-
59
- // endregion
60
-
61
- // region Device Info
62
-
63
- /**
64
- * 调用原生桥采集设备信息。
65
- * 失败时静默降级到 JS Platform API 填充基础字段。
66
- */
67
- async function fetchDeviceInfo() {
68
- try {
69
- return await _NativeRumSdkReactnative.default.getDeviceInfo();
70
- } catch (err) {
71
- console.warn('[rum] getDeviceInfo failed, falling back to JS defaults', err);
72
- return {
73
- os_type: _reactNative.Platform.OS === 'ios' ? 'iOS' : 'Android',
74
- os_version: String(_reactNative.Platform.Version ?? '')
75
- };
76
- }
77
- }
78
-
79
- /**
80
- * 模块级缓存,首次调用 fixAttrs 时懒初始化,避免模块加载时原生桥尚未就绪。
81
- * null 表示尚未触发采集。
82
- */
83
- let _cachedDeviceInfo = null;
84
-
85
- /**
86
- * 获取设备信息(懒初始化,仅触发一次原生桥调用)。
87
- */
88
- function getDeviceInfo() {
89
- if (!_cachedDeviceInfo) {
90
- _cachedDeviceInfo = fetchDeviceInfo();
91
- }
92
- return _cachedDeviceInfo;
93
- }
94
-
95
- // endregion
96
-
97
- /**
98
- * 将设备 / 系统 / 网络等公共属性注入 bundle。
99
- * 在 Reporter.request 中被调用;首次调用时懒触发设备信息采集。
100
- */
101
- const fixAttrs = async function (bundle) {
102
- if (!bundle) return;
103
- const native = await getDeviceInfo();
104
-
105
- // device.*
106
- const device = {
107
- id: native.device_id,
108
- type: native.device_type,
109
- brand: native.device_brand,
110
- model: native.device_model,
111
- name: native.device_name
112
- };
113
-
114
- // os.*
115
- const rnVersion = getReactNativeVersion();
116
- const os = {
117
- type: native.os_type ?? (_reactNative.Platform.OS === 'ios' ? 'iOS' : 'Android'),
118
- version: native.os_version ?? String(_reactNative.Platform.Version ?? ''),
119
- container: appName,
120
- container_version: rnVersion || undefined
121
- };
122
-
123
- // viewport:优先使用原生采集的物理像素,兜底 JS Dimensions(逻辑像素)
124
- let viewport;
125
- if (native.viewport_width && native.viewport_height) {
126
- viewport = {
127
- width: native.viewport_width,
128
- height: native.viewport_height
129
- };
130
- } else {
131
- try {
132
- const screen = _reactNative.Dimensions.get('screen');
133
- viewport = {
134
- width: Math.round(screen.width),
135
- height: Math.round(screen.height)
136
- };
137
- } catch {
138
- // 忽略
139
- }
140
- }
141
- bundle.app.type = _rumCore.AppType.reactnative;
142
- bundle.app.package = bundle.app.package ?? native.app_package;
143
- bundle.app.version = bundle.app.version ?? native.app_version;
144
- bundle._v = VERSION;
145
- bundle.device = {
146
- ...device,
147
- ...bundle.device
148
- };
149
- bundle.os = {
150
- ...os,
151
- ...bundle.os
152
- };
153
- if (viewport) {
154
- bundle.viewport = {
155
- ...bundle.viewport,
156
- ...viewport
157
- };
158
- }
159
- return bundle;
160
- };
161
- exports.fixAttrs = fixAttrs;
162
- //# sourceMappingURL=platform.js.map
1
+ "use strict";Object.defineProperty(exports,"__esModule",{value:!0}),exports.appName=exports.VERSION=void 0,exports.clearStorage=clearStorage,exports.fixAttrs=void 0,exports.getAllStorageKeys=getAllStorageKeys,exports.getStorage=getStorage,exports.removeStorage=removeStorage,exports.setStorage=setStorage;var _rumCore=require("@arms/rum-core"),_reactNative=require("react-native"),_NativeRumSdkReactnative=_interopRequireDefault(require("../NativeRumSdkReactnative"));function _interopRequireDefault(e){return e&&e.__esModule?e:{default:e}}const _pkg={version:"0.1.4-beta.1"},VERSION=exports.VERSION=_pkg.version,appName=exports.appName="react-native";function getReactNativeVersion(){try{return require("react-native/package.json").version??""}catch{const e=_reactNative.Platform.constants?.reactNativeVersion;return e?`${e.major}.${e.minor}.${e.patch}`:""}}function getStorage(e){return _NativeRumSdkReactnative.default.getItem(e)}function setStorage(e,t){return _NativeRumSdkReactnative.default.setItem(e,t)}function removeStorage(e){return _NativeRumSdkReactnative.default.removeItem(e)}function clearStorage(){return _NativeRumSdkReactnative.default.clear()}function getAllStorageKeys(){return _NativeRumSdkReactnative.default.getAllKeys()}async function fetchDeviceInfo(){try{return await _NativeRumSdkReactnative.default.getDeviceInfo()}catch(e){return console.warn("[rum] getDeviceInfo failed, falling back to JS defaults",e),{os_type:"ios"===_reactNative.Platform.OS?"iOS":"Android",os_version:String(_reactNative.Platform.Version??"")}}}let _cachedDeviceInfo=null;function getDeviceInfo(){return _cachedDeviceInfo||(_cachedDeviceInfo=fetchDeviceInfo()),_cachedDeviceInfo}const fixAttrs=async function(e){if(!e)return;const t=await getDeviceInfo(),r={id:t.device_id,type:t.device_type,brand:t.device_brand,model:t.device_model,name:t.device_name},a=getReactNativeVersion(),i={type:t.os_type??("ios"===_reactNative.Platform.OS?"iOS":"Android"),version:t.os_version??String(_reactNative.Platform.Version??""),container:appName,container_version:a||void 0};let o;if(t.viewport_width&&t.viewport_height)o={width:t.viewport_width,height:t.viewport_height};else try{const e=_reactNative.Dimensions.get("screen");o={width:Math.round(e.width),height:Math.round(e.height)}}catch{}return e.app.type=_rumCore.AppType.reactnative,e.app.package=e.app.package??t.app_package,e.app.version=e.app.version??t.app_version,e._v=VERSION,e.device={...r,...e.device},e.os={...i,...e.os},o&&(e.viewport={...e.viewport,...o}),e};exports.fixAttrs=fixAttrs;
@@ -1,158 +1 @@
1
- "use strict";
2
-
3
- Object.defineProperty(exports, "__esModule", {
4
- value: true
5
- });
6
- exports.RumSession = void 0;
7
- var _rumCore = require("@arms/rum-core");
8
- var _base = require("./base");
9
- var _view = require("./view");
10
- var _platform = require("./platform");
11
- // 存储userID的键名
12
- const USER_ID = '_rum_uid';
13
- // 旧版键名(用于迁移)
14
- const LEGACY_USER_ID = '_arms_uid';
15
- // 存储session
16
- // const RUM_SESSION = '_rum_session';
17
-
18
- class RumSession {
19
- /** 平台类型标识 */
20
- appType = 'reactnative';
21
-
22
- /** SDK 版本号(延迟导入避免循环依赖) */
23
- get sdkVersion() {
24
- return require('./platform').VERSION;
25
- }
26
-
27
- // @ts-ignore
28
-
29
- // private sessionId = '';
30
-
31
- session = '';
32
- userId = '';
33
- constructor() {
34
- this.initUser();
35
- }
36
- init(ctx) {
37
- this.ctx = ctx;
38
- this.sessionConfig = this.fixSessionConfig(ctx.config?.sessionConfig);
39
- }
40
- getSessionId() {
41
- return this.getSessionInfo().sessionId;
42
- }
43
- getSampled() {
44
- return this.getSessionInfo().sampled;
45
- }
46
- checkSession(info) {
47
- const {
48
- overtime = 0,
49
- maxDuration = 0
50
- } = this.sessionConfig;
51
- const now = (0, _base.getCurrentTime)();
52
- return !(info.startTime + maxDuration < now || info.lastTime + overtime < now);
53
- }
54
- updateSession() {
55
- const info = this.getSessionInfo();
56
- if (info.isNew) {
57
- return;
58
- }
59
- const startTime = info.startTime;
60
- const lastTime = (0, _base.getCurrentTime)();
61
- const sampled = info.sampled ? 1 : 0;
62
- this.session = `${info.sessionId}-${sampled}-${startTime}-${lastTime}`;
63
- // setStorage(RUM_SESSION, `${info.sessionId}-${sampled}-${startTime}-${lastTime}`)
64
- }
65
- getSessionInfo() {
66
- const [sid, sampled, startTime, lastTime] = this.session.split('-');
67
- let info = {
68
- sessionId: sid,
69
- sampled: sampled !== '0',
70
- startTime: parseInt(startTime || '', 10) || 0,
71
- lastTime: parseInt(lastTime || '', 10) || 0
72
- };
73
- if (!this.checkSession(info)) {
74
- info = this.resetSession();
75
- }
76
- return info;
77
- }
78
- getEventId() {
79
- const sid = this.getSessionId();
80
- return (0, _rumCore.generateEventId)(sid);
81
- }
82
- getViewId() {
83
- return this.getUUID();
84
- }
85
- async initUser() {
86
- this.userId = await (0, _platform.getStorage)(USER_ID);
87
- // 迁移旧版键名 _arms_uid → _rum_uid
88
- if (!this.userId) {
89
- const legacyId = await (0, _platform.getStorage)(LEGACY_USER_ID);
90
- if (legacyId) {
91
- this.userId = legacyId;
92
- await (0, _platform.setStorage)(USER_ID, this.userId);
93
- return;
94
- }
95
- }
96
- if (!this.userId) {
97
- this.userId = `uid_${(0, _rumCore.generateSpanId)(16, 36)}`;
98
- await (0, _platform.setStorage)(USER_ID, this.userId);
99
- }
100
- }
101
- getUserId() {
102
- return this.userId;
103
- }
104
- resetSession() {
105
- const {
106
- sampleRate = 1
107
- } = this.sessionConfig;
108
- const sid = this.getUUID();
109
- const now = (0, _base.getCurrentTime)();
110
- const sampled = (0, _rumCore.performDraw)(sampleRate * 100);
111
- this.session = `${sid}-${sampled ? 1 : 0}-${now}-${now}`;
112
- // setStorage(RUM_SESSION, this.session);
113
- return {
114
- sessionId: sid,
115
- sampled: sampled,
116
- startTime: now,
117
- lastTime: now,
118
- isNew: true
119
- };
120
- }
121
- getUUID() {
122
- return (0, _rumCore.generateGUID)().replace(/-/g, '');
123
- }
124
- fixSessionConfig(sessionConfig = {}) {
125
- let {
126
- sampleRate,
127
- maxDuration,
128
- overtime
129
- } = sessionConfig;
130
- if (!(0, _rumCore.isNumber)(sampleRate) || sampleRate < 0 || sampleRate > 1) {
131
- sampleRate = 1;
132
- }
133
- if (!(0, _rumCore.isNumber)(maxDuration) || maxDuration < 4 * _rumCore.ONE_HOUR || maxDuration > _rumCore.ONE_DAY) {
134
- maxDuration = _rumCore.ONE_DAY;
135
- }
136
- if (!(0, _rumCore.isNumber)(overtime) || overtime > _rumCore.ONE_HOUR || overtime < 10 * _rumCore.ONE_MINUTE) {
137
- overtime = 30 * _rumCore.ONE_MINUTE;
138
- }
139
- return {
140
- sampleRate,
141
- maxDuration,
142
- overtime
143
- };
144
- }
145
- getBaseEvent() {
146
- const session_id = this.getSessionId();
147
- const event_id = this.getEventId();
148
- return {
149
- timestamp: (0, _base.getCurrentTime)(),
150
- session_id,
151
- event_id,
152
- view: this.ctx ? (0, _view.getCurView)(this.ctx) : undefined,
153
- times: 1
154
- };
155
- }
156
- }
157
- exports.RumSession = RumSession;
158
- //# sourceMappingURL=session.js.map
1
+ "use strict";Object.defineProperty(exports,"__esModule",{value:!0}),exports.RumSession=void 0;var _rumCore=require("@arms/rum-core"),_base=require("./base"),_view=require("./view"),_platform=require("./platform");const USER_ID="_rum_uid",LEGACY_USER_ID="_arms_uid";class RumSession{appType="reactnative";get sdkVersion(){return require("./platform").VERSION}session="";userId="";constructor(){this.initUser()}init(e){this.ctx=e,this.sessionConfig=this.fixSessionConfig(e.config?.sessionConfig)}getSessionId(){return this.getSessionInfo().sessionId}getSampled(){return this.getSessionInfo().sampled}checkSession(e){const{overtime:s=0,maxDuration:t=0}=this.sessionConfig,r=(0,_base.getCurrentTime)();return!(e.startTime+t<r||e.lastTime+s<r)}updateSession(){const e=this.getSessionInfo();if(e.isNew)return;const s=e.startTime,t=(0,_base.getCurrentTime)(),r=e.sampled?1:0;this.session=`${e.sessionId}-${r}-${s}-${t}`}getSessionInfo(){const[e,s,t,r]=this.session.split("-");let i={sessionId:e,sampled:"0"!==s,startTime:parseInt(t||"",10)||0,lastTime:parseInt(r||"",10)||0};return this.checkSession(i)||(i=this.resetSession()),i}getEventId(){const e=this.getSessionId();return(0,_rumCore.generateEventId)(e)}getViewId(){return this.getUUID()}async initUser(){if(this.userId=await(0,_platform.getStorage)(USER_ID),!this.userId){const e=await(0,_platform.getStorage)("_arms_uid");if(e)return this.userId=e,void await(0,_platform.setStorage)(USER_ID,this.userId)}this.userId||(this.userId=`uid_${(0,_rumCore.generateSpanId)(16,36)}`,await(0,_platform.setStorage)(USER_ID,this.userId))}getUserId(){return this.userId}resetSession(){const{sampleRate:e=1}=this.sessionConfig,s=this.getUUID(),t=(0,_base.getCurrentTime)(),r=(0,_rumCore.performDraw)(100*e);return this.session=`${s}-${r?1:0}-${t}-${t}`,{sessionId:s,sampled:r,startTime:t,lastTime:t,isNew:!0}}getUUID(){return(0,_rumCore.generateGUID)().replace(/-/g,"")}fixSessionConfig(e={}){let{sampleRate:s,maxDuration:t,overtime:r}=e;return(!(0,_rumCore.isNumber)(s)||s<0||s>1)&&(s=1),(!(0,_rumCore.isNumber)(t)||t<4*_rumCore.ONE_HOUR||t>_rumCore.ONE_DAY)&&(t=_rumCore.ONE_DAY),(!(0,_rumCore.isNumber)(r)||r>_rumCore.ONE_HOUR||r<10*_rumCore.ONE_MINUTE)&&(r=30*_rumCore.ONE_MINUTE),{sampleRate:s,maxDuration:t,overtime:r}}getBaseEvent(){const e=this.getSessionId(),s=this.getEventId();return{timestamp:(0,_base.getCurrentTime)(),session_id:e,event_id:s,view:this.ctx?(0,_view.getCurView)(this.ctx):void 0,times:1}}}exports.RumSession=RumSession;
@@ -1,59 +1 @@
1
- "use strict";
2
-
3
- Object.defineProperty(exports, "__esModule", {
4
- value: true
5
- });
6
- exports.getPathByURL = getPathByURL;
7
- exports.getURL = getURL;
8
- /**
9
- * 根据指定 URL 获取视图的名称,默认为其path部分
10
- * @param url 需要提取路径部分的 URL
11
- * @param isHash 是否为 hash 模式路由的 URL
12
- */
13
- function getPathByURL(url, isHash = false) {
14
- try {
15
- const urlObj = getURL(url);
16
- if (!urlObj) return;
17
- if (isHash) {
18
- return urlObj.hash;
19
- } else {
20
- return urlObj.pathname;
21
- }
22
- } catch (error) {
23
- return '';
24
- }
25
- }
26
-
27
- // /**
28
- // * 检查是否为上报域名
29
- // * @param ctx
30
- // * @param url 需要提取路径部分的 URL
31
- // */
32
- // export function isEndpoint(ctx: IContext, url: string): boolean {
33
- // const { endpoint } = ctx.getConfig();
34
- // try {
35
- // return getURL(url).hostname === getURL(endpoint).hostname
36
- // } catch (e) {
37
- // return false;
38
- // }
39
- // }
40
-
41
- const REGEX = /^(?:([^:\/?#]+):\/\/)?((?:([^\/?#@]*)@)?([^\/?#:]*)(?:\:(\d*))?)?([^?#]*)(?:\?([^#]*))?(?:#((?:.|\n)*))?/i;
42
- function getURL(url) {
43
- const parts = decodeURIComponent(url).match(REGEX);
44
- if (!parts) return null;
45
- const auth = (parts[3] || '').split(':');
46
- const host = auth.length ? (parts[2] || '').replace(/(.*\@)/, '') : parts[2];
47
- return {
48
- uri: parts[0],
49
- protocol: parts[1],
50
- host: host,
51
- hostname: parts[4],
52
- port: parts[5],
53
- pathname: parts[6],
54
- search: parts[7],
55
- // query: mapSearchParams(parts[7]),
56
- hash: parts[8]
57
- };
58
- }
59
- //# sourceMappingURL=url.js.map
1
+ "use strict";function getPathByURL(t,e=!1){try{const n=getURL(t);if(!n)return;return e?n.hash:n.pathname}catch(t){return""}}Object.defineProperty(exports,"__esModule",{value:!0}),exports.getPathByURL=getPathByURL,exports.getURL=getURL;const REGEX=/^(?:([^:\/?#]+):\/\/)?((?:([^\/?#@]*)@)?([^\/?#:]*)(?:\:(\d*))?)?([^?#]*)(?:\?([^#]*))?(?:#((?:.|\n)*))?/i;function getURL(t){const e=decodeURIComponent(t).match(REGEX);if(!e)return null;const n=(e[3]||"").split(":").length?(e[2]||"").replace(/(.*\@)/,""):e[2];return{uri:e[0],protocol:e[1],host:n,hostname:e[4],port:e[5],pathname:e[6],search:e[7],hash:e[8]}}
@@ -1,93 +1 @@
1
- "use strict";
2
-
3
- Object.defineProperty(exports, "__esModule", {
4
- value: true
5
- });
6
- exports.addNavigateListener = addNavigateListener;
7
- exports.getCurView = getCurView;
8
- exports.removeNavigateListener = removeNavigateListener;
9
- exports.startTrackingViews = startTrackingViews;
10
- exports.stopTrackingViews = stopTrackingViews;
11
- var _rumCore = require("@arms/rum-core");
12
- // import { IPage } from "../types/client";
13
-
14
- // export const PAGE_ID = '__rum_view_id';
15
- //
16
- // /**
17
- // * 获取 RUM 内置的view_id标识
18
- // * @param page
19
- // * @param session
20
- // * @returns
21
- // */
22
- // export async function getRumViewId(page: IPage, session?: IRumSession): Promise<string> {
23
- // if (!page) return;
24
- // if (page.id) {
25
- // return page.id;
26
- // }
27
- // if (!session) return;
28
- // return page.id = session.getViewId();
29
- // }
30
- //
31
- // /**
32
- // * 获取当前 view
33
- // * @param viewId
34
- // * @param ctx
35
- // * @returns
36
- // */
37
- // export function getViewById(viewId: string, ctx: IContext): IViewData {
38
- // if (!viewId || !ctx) return;
39
- // return ctx.getViews().find(view => view.id === viewId);
40
- // }
41
-
42
- /**
43
- * 获取当前 view
44
- * @param ctx
45
- * @returns
46
- */
47
- function getCurView(ctx) {
48
- if (!ctx) return;
49
- const views = ctx.getViews();
50
- if (views && views.length) {
51
- return views[views.length - 1];
52
- }
53
- return null;
54
- }
55
- let currentNavigationRef;
56
- const navigateListeners = [];
57
- function addNavigateListener(listener) {
58
- if ((0, _rumCore.isFunction)(listener)) {
59
- navigateListeners.push(listener);
60
- }
61
- }
62
- function removeNavigateListener(listener) {
63
- navigateListeners.splice(navigateListeners.indexOf(listener), 1);
64
- }
65
- function triggerNavigateChange(event) {
66
- if (!currentNavigationRef) return;
67
- let route = event;
68
- if ((0, _rumCore.isFunction)(currentNavigationRef.getCurrentRoute)) {
69
- route = currentNavigationRef.getCurrentRoute();
70
- }
71
- if (!route) return;
72
- navigateListeners.forEach(listener => {
73
- listener(route);
74
- });
75
- }
76
- function startTrackingViews(nav) {
77
- if (!nav || currentNavigationRef) return;
78
- currentNavigationRef = nav;
79
- if ((0, _rumCore.isFunction)(nav.events)) {
80
- // react-native-navigation
81
- nav.events().registerComponentDidAppearListener(triggerNavigateChange);
82
- } else {
83
- // @react-native/navigation
84
- nav.addListener('state', triggerNavigateChange);
85
- }
86
- triggerNavigateChange({});
87
- }
88
- function stopTrackingViews() {
89
- if (!currentNavigationRef) return;
90
- currentNavigationRef.removeListener('state', triggerNavigateChange);
91
- currentNavigationRef = undefined;
92
- }
93
- //# sourceMappingURL=view.js.map
1
+ "use strict";Object.defineProperty(exports,"__esModule",{value:!0}),exports.addNavigateListener=addNavigateListener,exports.getCurView=getCurView,exports.removeNavigateListener=removeNavigateListener,exports.startTrackingViews=startTrackingViews,exports.stopTrackingViews=stopTrackingViews;var _rumCore=require("@arms/rum-core");function getCurView(e){if(!e)return;const t=e.getViews();return t&&t.length?t[t.length-1]:null}let currentNavigationRef;const navigateListeners=[];function addNavigateListener(e){(0,_rumCore.isFunction)(e)&&navigateListeners.push(e)}function removeNavigateListener(e){navigateListeners.splice(navigateListeners.indexOf(e),1)}function triggerNavigateChange(e){if(!currentNavigationRef)return;let t=e;(0,_rumCore.isFunction)(currentNavigationRef.getCurrentRoute)&&(t=currentNavigationRef.getCurrentRoute()),t&&navigateListeners.forEach(e=>{e(t)})}function startTrackingViews(e){e&&!currentNavigationRef&&(currentNavigationRef=e,(0,_rumCore.isFunction)(e.events)?e.events().registerComponentDidAppearListener(triggerNavigateChange):e.addListener("state",triggerNavigateChange),triggerNavigateChange({}))}function stopTrackingViews(){currentNavigationRef&&(currentNavigationRef.removeListener("state",triggerNavigateChange),currentNavigationRef=void 0)}
@@ -1,51 +1 @@
1
- "use strict";
2
-
3
- import { NativeModules, TurboModuleRegistry } from 'react-native';
4
-
5
- /**
6
- * 原生设备信息,对应存储模型中的公共属性:
7
- * - device.* (id / type / brand / model / name)
8
- * - os.* (type / version / container / container_version)
9
- * - app.package
10
- * - viewport.width / viewport.height
11
- */
12
-
13
- /**
14
- * 获取原生模块。
15
- *
16
- * 优先使用 TurboModuleRegistry(RN 0.68+ TurboModule 架构),
17
- * 若未找到则降级到 Legacy Bridge 的 NativeModules(RN 0.68-0.70 未开启 New Arch 时),
18
- * 若均不可用则返回一组空实现兜底。
19
- *
20
- * 使用非强制的 `TurboModuleRegistry.get`(而非 `getEnforcing`),避免在原生
21
- * 二进制未注册该模块时于「模块加载阶段」直接抛异常——那会连锁导致整个 JS
22
- * bundle 评估失败(表现为所有路由丢失 default export、App 白屏)。
23
- *
24
- * 当原生模块缺失时(通常是新增原生代码后未重新编译原生 App,只重跑了 Metro),
25
- * 返回一组空实现兜底:崩溃采集与原生设备信息降级为不可用,但 PV / 行为 / API /
26
- * JS 异常等纯 JS 能力不受影响。需重新构建原生工程(如 `expo run:ios` /
27
- * `pod install` + 重新编译)后崩溃采集才会真正生效。
28
- */
29
- const nativeModule = TurboModuleRegistry.get('RumSdkReactnative') ?? NativeModules.RumSdkReactnative;
30
- if (!nativeModule) {
31
- console.warn("[rum] Native module 'RumSdkReactnative' not found in the native binary. " + 'Crash reporting and native device info are disabled. ' + 'Rebuild the native app (e.g. `expo run:ios` / `expo run:android`, ' + 'or `pod install` + rebuild) so the module gets registered.');
32
- }
33
-
34
- /** 原生模块缺失时的空实现,保证调用方不会因缺方法而抛错。 */
35
- const fallback = {
36
- getItem: async () => null,
37
- setItem: async () => {},
38
- removeItem: async () => {},
39
- clear: async () => {},
40
- getAllKeys: async () => [],
41
- getDeviceInfo: async () => ({}),
42
- getPendingCrashes: async () => '[]',
43
- clearCrashReports: async () => {},
44
- clearAllCrashReports: async () => {},
45
- cleanupOldCrashes: async () => {},
46
- crashedLastRun: async () => false,
47
- updateCrashContext: () => {},
48
- triggerTestCrash: () => {}
49
- };
50
- export default nativeModule ?? fallback;
51
- //# sourceMappingURL=NativeRumSdkReactnative.js.map
1
+ "use strict";import{NativeModules,TurboModuleRegistry}from"react-native";const nativeModule=TurboModuleRegistry.get("RumSdkReactnative")??NativeModules.RumSdkReactnative;nativeModule||console.warn("[rum] Native module 'RumSdkReactnative' not found in the native binary. Crash reporting and native device info are disabled. Rebuild the native app (e.g. `expo run:ios` / `expo run:android`, or `pod install` + rebuild) so the module gets registered.");const fallback={getItem:async()=>null,setItem:async()=>{},removeItem:async()=>{},clear:async()=>{},getAllKeys:async()=>[],getDeviceInfo:async()=>({}),getPendingCrashes:async()=>"[]",clearCrashReports:async()=>{},clearAllCrashReports:async()=>{},cleanupOldCrashes:async()=>{},crashedLastRun:async()=>!1,updateCrashContext:()=>{},triggerTestCrash:()=>{},getPendingOomReports:async()=>"[]",clearOomReports:async()=>{},updateCollectorsConfig:()=>{}};export default nativeModule??fallback;
@@ -1,103 +1 @@
1
- "use strict";
2
-
3
- import { RumEventType } from '@arms/rum-core';
4
- import { getCurView } from "../../utils/view.js";
5
- import { addActionListener, removeActionListener, startTrackingActions, stopTrackingActions } from "../../utils/action.js";
6
- export default class ActionCollector {
7
- name = 'action-collector';
8
- DELAY_TIME = 300;
9
- events = ['tap'];
10
- setup(ctx, sendEvent) {
11
- const {
12
- collectors = {}
13
- } = ctx.getConfig();
14
- if (collectors.action === false) {
15
- return;
16
- }
17
- this.ctx = ctx;
18
- this.sendEvent = sendEvent;
19
- // 开启 React Native 触摸自动采集,并监听标准化的 tap 事件
20
- startTrackingActions();
21
- addActionListener(this.onEvent);
22
- }
23
- onEvent = e => {
24
- if (e && this.events.includes(e.type) && e.target) {
25
- const {
26
- target,
27
- currentTarget,
28
- type
29
- } = e;
30
- const {
31
- dataset,
32
- id
33
- } = target;
34
- if (!id) return;
35
- if (currentTarget && id !== currentTarget.id) return;
36
- let view;
37
- if (this.ctx) {
38
- view = getCurView(this.ctx);
39
- }
40
- const event = {
41
- event_type: RumEventType.ACTION,
42
- type,
43
- name: e.name || id,
44
- target_name: e.targetName,
45
- duration: e.duration,
46
- position: e.position,
47
- target: this.buildTarget(target),
48
- snapshots: dataset && Object.keys(dataset).length ? JSON.stringify(dataset).slice(0, 1000) : undefined,
49
- times: 1,
50
- view
51
- };
52
- clearTimeout(this.timer);
53
- if (this.lastEvent && this.lastActionId === id) {
54
- // 同一元素的连续点击:仅累加次数
55
- // @ts-ignore
56
- this.lastEvent.times += 1;
57
- } else {
58
- // 切换到不同元素:立即上报上一个,再记录新事件
59
- if (this.lastEvent) {
60
- this.sendAction();
61
- }
62
- this.lastEvent = event;
63
- this.lastActionId = id;
64
- }
65
- this.timer = setTimeout(this.sendAction, this.DELAY_TIME);
66
- }
67
- };
68
-
69
- /**
70
- * 组装热力图相关的 target 信息(selector/宽高/可交互性/可信度)。
71
- * 当没有任何字段时返回 undefined,避免上报空对象。
72
- */
73
- buildTarget(target) {
74
- const {
75
- selector,
76
- width,
77
- height,
78
- reaction,
79
- trust
80
- } = target;
81
- if (selector === undefined && width === undefined && height === undefined && reaction === undefined && trust === undefined) {
82
- return undefined;
83
- }
84
- return {
85
- selector,
86
- width,
87
- height,
88
- reaction,
89
- trust
90
- };
91
- }
92
- sendAction = () => {
93
- // @ts-ignore
94
- this.sendEvent(this.lastEvent);
95
- this.lastEvent = undefined;
96
- this.lastActionId = undefined;
97
- };
98
- destroy() {
99
- removeActionListener(this.onEvent);
100
- stopTrackingActions();
101
- }
102
- }
103
- //# sourceMappingURL=index.js.map
1
+ "use strict";import{RumEventType}from"@arms/rum-core";import{getCurView}from"../../utils/view.js";import{addActionListener,removeActionListener,startTrackingActions,stopTrackingActions}from"../../utils/action.js";export default class ActionCollector{name="action-collector";DELAY_TIME=300;events=["tap"];setup(t,e){const{collectors:i={}}=t.getConfig();!1!==i.action&&(this.ctx=t,this.sendEvent=e,startTrackingActions(),addActionListener(this.onEvent))}onEvent=t=>{if(t&&this.events.includes(t.type)&&t.target){const{target:e,currentTarget:i,type:s}=t,{dataset:n,id:o}=e;if(!o)return;if(i&&o!==i.id)return;let r;this.ctx&&(r=getCurView(this.ctx));const c={event_type:RumEventType.ACTION,type:s,name:t.name||o,target_name:t.targetName,duration:t.duration,position:t.position,target:this.buildTarget(e),snapshots:n&&Object.keys(n).length?JSON.stringify(n).slice(0,1e3):void 0,times:1,view:r};clearTimeout(this.timer),this.lastEvent&&this.lastActionId===o?this.lastEvent.times+=1:(this.lastEvent&&this.sendAction(),this.lastEvent=c,this.lastActionId=o),this.timer=setTimeout(this.sendAction,this.DELAY_TIME)}};buildTarget(t){const{selector:e,width:i,height:s,reaction:n,trust:o}=t;if(void 0!==e||void 0!==i||void 0!==s||void 0!==n||void 0!==o)return{selector:e,width:i,height:s,reaction:n,trust:o}}sendAction=()=>{this.sendEvent(this.lastEvent),this.lastEvent=void 0,this.lastActionId=void 0};destroy(){removeActionListener(this.onEvent),stopTrackingActions()}}