xbx 3 месяцев назад
Родитель
Сommit
16756c6056
8 измененных файлов с 1808 добавлено и 9 удалено
  1. 18 0
      .oxlintrc.json
  2. 13 7
      package.json
  3. 1425 1
      pnpm-lock.yaml
  4. 1 1
      rollup.config.js
  5. 24 0
      src/test.js
  6. 111 0
      test/index.html
  7. 132 0
      test/test-cjs.js
  8. 84 0
      test/test-esm.html

+ 18 - 0
.oxlintrc.json

@@ -0,0 +1,18 @@
+{
+  "rules": {
+    "no-unused-vars": "error",
+    "no-redeclare": "error",
+    "no-const-assign": "error",
+    "no-unreachable": "error",
+    "no-duplicate-case": "error",
+    "no-fallthrough": "warn",
+    "no-compare-neg-zero": "error",
+    "no-debugger": "warn",
+    "no-async-promise-executor": "warn",
+    "no-empty": "warn",
+    "no-extra-boolean-cast": "warn",
+    "no-sparse-arrays": "warn",
+    "prefer-const": "warn",
+    "no-var": "warn"
+  }
+}

+ 13 - 7
package.json

@@ -8,17 +8,20 @@
 		"dev": "rollup -c -w",
 		"build:prod": "rollup -c --environment NODE_ENV:production",
 		"test": "echo \"Error: no test specified\" && exit 1",
-		"lint": "eslint src/",
+		"lint": "oxlint src/",
+		"lint:fix": "oxlint --fix src/",
 		"prebuild": "if exist dist (rmdir /s /q dist) || echo dist does not exist"
 	},
-	"dependencies": {
-		"rollup": "^4.54.0"
-	},
 	"devDependencies": {
-		"@rollup/plugin-node-resolve": "^15.2.3",
 		"@rollup/plugin-commonjs": "^25.0.7",
+		"@rollup/plugin-node-resolve": "^15.2.3",
 		"@rollup/plugin-terser": "^0.4.4",
-		"eslint": "^8.56.0"
+		"lint-staged": "^16.2.7",
+		"oxlint": "^1.39.0",
+		"rollup": "^4.54.0",
+		"rollup-plugin-typescript2": "^0.36.0",
+		"ts-loader": "^9.5.4",
+		"typescript": "^5.9.3"
 	},
 	"keywords": [
 		"monitoring",
@@ -29,5 +32,8 @@
 		"sdk"
 	],
 	"author": "Internal Team",
-	"license": "MIT"
+	"license": "MIT",
+	"lint-staged": {
+		"*.{js,jsx,ts,tsx,mjs,cjs}": "pnpm run lint"
+	}
 }

Разница между файлами не показана из-за своего большого размера
+ 1425 - 1
pnpm-lock.yaml


+ 1 - 1
rollup.config.js

@@ -4,7 +4,7 @@ import commonjs from '@rollup/plugin-commonjs';
 import terser from '@rollup/plugin-terser';
 
 export default defineConfig({
-  input: 'src/main.js',
+  input: 'src/test.js',
   output: [
     {
       file: 'dist/bundle-iife.js',

+ 24 - 0
src/test.js

@@ -0,0 +1,24 @@
+// 浏览器和Node.js通用的测试函数
+
+function test(a) {
+  return a + 1;
+}
+
+function testExport(a) {
+  let b = a + 1;
+  return test(b);
+}
+
+// 将函数暴露到全局对象,以便在浏览器中使用
+if (typeof window !== 'undefined') {
+  window.test = test;
+  window.testExport = testExport;
+}
+
+// 保持ES模块导出兼容性
+if (typeof exports !== 'undefined') {
+  module.exports = { test, testExport };
+} else {
+  // 对于ES模块,可以这样导出
+  // 但当作为脚本标签引入时,函数已在全局可用
+}

+ 111 - 0
test/index.html

@@ -0,0 +1,111 @@
+<!DOCTYPE html>
+<html lang="zh-CN">
+<head>
+    <meta charset="UTF-8">
+    <meta name="viewport" content="width=device-width, initial-scale=1.0">
+    <title>Monitor SDK 测试页面</title>
+</head>
+<body>
+    <h1>监控SDK测试页面</h1>
+    <p>此页面用于测试打包后的监控SDK是否正常工作。</p>
+    
+    <!-- 引入打包后的测试函数 -->
+    <script src="../dist/bundle-iife.js"></script>
+    
+    <div id="test-container">
+        <button id="trigger-error">触发JavaScript错误</button>
+        <button id="trigger-promise-error">触发Promise错误</button>
+        <button id="simulate-performance-event">模拟性能事件</button>
+        <button id="send-custom-data">发送自定义数据</button>
+        <button id="test-functions">测试函数(test)</button>
+    </div>
+    
+    <div id="result">
+        <h3>控制台输出:</h3>
+        <p>请打开开发者工具查看监控SDK的输出信息</p>
+    </div>
+
+    <script>
+        // 页面加载完成后执行测试
+        document.addEventListener('DOMContentLoaded', function() {
+            console.log('页面已加载,监控SDK应该已经初始化');
+            
+            // 检查监控SDK是否已正确加载
+            if (window.MonitorSDK && window.monitorInstance) {
+                console.log('监控SDK已成功加载');
+                console.log('SDK实例:', window.monitorInstance);
+            } else {
+                console.error('监控SDK未正确加载');
+            }
+
+            // 测试全局函数是否存在
+            if (window.test && window.testExport) {
+                console.log('✅ 全局函数已成功加载');
+                
+                // 测试函数功能
+                console.log('test(5) =', window.test(5));
+                console.log('testExport(5) =', window.testExport(5));
+            } else {
+                console.error('❌ 全局函数未找到');
+            }
+            
+            // 绑定按钮事件
+            document.getElementById('test-functions').addEventListener('click', function() {
+                console.log('测试全局函数');
+                
+                if (window.test && window.testExport) {
+                    const result1 = window.test(10);
+                    const result2 = window.testExport(10);
+                    
+                    console.log('window.test(10) =', result1);
+                    console.log('window.testExport(10) =', result2);
+                    
+                    alert(`函数调用结果:\ntest(10) = ${result1}\ntestExport(10) = ${result2}`);
+                } else {
+                    console.error('函数未定义');
+                    alert('函数未定义');
+                }
+            });
+            
+            document.getElementById('trigger-error').addEventListener('click', function() {
+                console.log('触发JavaScript错误测试');
+                // 触发一个JavaScript错误
+                throw new Error('这是测试错误');
+            });
+
+            document.getElementById('trigger-promise-error').addEventListener('click', function() {
+                console.log('触发Promise错误测试');
+                // 触发一个Promise错误
+                Promise.reject(new Error('这是测试Promise错误'));
+            });
+            
+            document.getElementById('simulate-performance-event').addEventListener('click', function() {
+                console.log('模拟性能事件');
+                // 这会触发性能监控
+                const start = performance.now();
+                // 模拟一些计算
+                for(let i = 0; i < 1000000; i++) {}
+                const end = performance.now();
+                console.log(`模拟计算耗时: ${end - start} ms`);
+            });
+            
+            document.getElementById('send-custom-data').addEventListener('click', function() {
+                console.log('发送自定义数据');
+                // 使用监控实例发送自定义数据
+                if (window.monitorInstance) {
+                    window.monitorInstance.reportData({
+                        type: 'custom_event',
+                        message: '自定义事件测试',
+                        timestamp: Date.now()
+                    });
+                }
+            });
+        });
+        
+        // 页面可见性变化事件(用于测试页面停留时间监控)
+        document.addEventListener('visibilitychange', function() {
+            console.log('页面可见性变化:', document.visibilityState);
+        });
+    </script>
+</body>
+</html>

+ 132 - 0
test/test-cjs.js

@@ -0,0 +1,132 @@
+/**
+ * 测试CommonJS格式的监控SDK bundle
+ */
+
+// 在Node.js环境中测试CJS格式的bundle
+console.log('开始测试CommonJS格式的监控SDK');
+
+try {
+  // 动态引入CJS格式的bundle
+  const MonitorSDK = require('../dist/bundle-cjs.js');
+  
+  console.log('CommonJS格式的监控SDK已加载');
+  console.log('MonitorSDK类型:', typeof MonitorSDK);
+  
+  // 注意:由于Node.js环境缺少浏览器API(如window、document、performance等)
+  // 直接初始化可能会出错,所以我们只测试基本导入功能
+  
+  // 检查MonitorSDK构造函数是否存在
+  if (typeof MonitorSDK === 'function') {
+    console.log('✅ MonitorSDK构造函数存在');
+  } else {
+    console.log('❌ MonitorSDK不是函数');
+  }
+  
+  console.log('\n注意:由于Node.js环境缺少浏览器API,完整的SDK功能无法在此环境中测试。');
+  console.log('完整的功能测试需要在浏览器环境中进行。');
+  
+} catch (error) {
+  console.error('❌ 加载CommonJS格式的bundle时出错:', error.message);
+}
+
+// 模拟浏览器环境的部分功能以测试SDK
+console.log('\n--- 模拟浏览器环境测试 ---');
+
+// 为Node.js环境模拟必要的浏览器API
+global.window = global;
+global.document = {
+  addEventListener: function(event, handler) {
+    console.log(`模拟添加${event}事件监听器`);
+  }
+};
+global.performance = {
+  timing: {
+    navigationStart: Date.now(),
+    domainLookupStart: Date.now(),
+    domainLookupEnd: Date.now() + 1,
+    connectStart: Date.now() + 1,
+    connectEnd: Date.now() + 2,
+    requestStart: Date.now() + 2,
+    responseStart: Date.now() + 3,
+    responseEnd: Date.now() + 4,
+    domLoading: Date.now() + 5,
+    domContentLoadedEventStart: Date.now() + 6,
+    domContentLoadedEventEnd: Date.now() + 7,
+    loadEventStart: Date.now() + 8,
+    loadEventEnd: Date.now() + 9
+  },
+  getEntriesByType: function(type) {
+    console.log(`模拟获取${type}类型的性能条目`);
+    return [];
+  }
+};
+global.navigator = {
+  userAgent: 'Test Node Environment',
+  sendBeacon: function(url, data) {
+    console.log('模拟sendBeacon调用:', url, data);
+    return true;
+  }
+};
+global.fetch = function(url, options) {
+  console.log('模拟fetch调用:', url, options);
+  return Promise.resolve({
+    ok: true,
+    json: () => Promise.resolve({})
+  });
+};
+
+// 现在尝试动态加载并初始化SDK
+setTimeout(() => {
+  try {
+    // 重新require以确保使用新的全局变量
+    delete require.cache[require.resolve('../dist/bundle-cjs.js')];
+    const MonitorSDK = require('../dist/bundle-cjs.js');
+    
+    // 创建实例
+    const monitor = new MonitorSDK({
+      appId: 'test-app',
+      apiUrl: 'http://localhost:3000/api/monitor',
+      enableErrorTracking: true,
+      enablePerformanceTracking: true,
+      enableUserBehaviorTracking: false, // 避免在Node.js中使用document
+      enableResourceTracking: true,
+      sampleRate: 1.0
+    });
+    
+    console.log('✅ 成功创建MonitorSDK实例');
+    
+    // 测试错误上报功能
+    if (monitor && typeof monitor.reportError === 'function') {
+      console.log('✅ reportError方法存在');
+      
+      monitor.reportError({
+        type: 'test_error',
+        message: '测试错误',
+        timestamp: Date.now()
+      });
+      
+      console.log('✅ 成功调用reportError方法');
+    } else {
+      console.log('❌ reportError方法不存在');
+    }
+    
+    // 测试数据上报功能
+    if (monitor && typeof monitor.reportData === 'function') {
+      console.log('✅ reportData方法存在');
+      
+      monitor.reportData({
+        type: 'test_data',
+        message: '测试数据',
+        timestamp: Date.now()
+      });
+      
+      console.log('✅ 成功调用reportData方法');
+    } else {
+      console.log('❌ reportData方法不存在');
+    }
+    
+  } catch (error) {
+    console.error('❌ 在模拟环境中初始化SDK时出错:', error.message);
+    console.error('堆栈:', error.stack);
+  }
+}, 100);

+ 84 - 0
test/test-esm.html

@@ -0,0 +1,84 @@
+<!DOCTYPE html>
+<html lang="zh-CN">
+<head>
+    <meta charset="UTF-8">
+    <meta name="viewport" content="width=device-width, initial-scale=1.0">
+    <title>ESM格式监控SDK测试</title>
+</head>
+<body>
+    <h1>ESM格式监控SDK测试页面</h1>
+    <p>此页面用于测试ES模块格式的监控SDK是否正常工作。</p>
+    
+    <div id="test-container">
+        <button id="test-esm-sdk">测试ESM格式SDK</button>
+        <button id="test-esm-functionality">测试ESM功能</button>
+    </div>
+    
+    <div id="result">
+        <h3>控制台输出:</h3>
+        <p>请打开开发者工具查看监控SDK的输出信息</p>
+    </div>
+
+    <!-- 使用ES模块语法导入SDK -->
+    <script type="module">
+        // 从ESM格式的bundle中导入
+        // 注意:由于我们的bundle没有导出默认对象,我们需要使用动态导入
+        console.log('开始测试ESM格式的监控SDK');
+        
+        // 动态导入ESM格式的bundle
+        import('../dist/bundle-esm.js').then(module => {
+            console.log('ESM格式的监控SDK已加载');
+            console.log('模块内容:', module);
+            
+            // 检查全局对象是否可用(我们的代码会在全局作用域创建实例)
+            if (window.MonitorSDK && window.monitorInstance) {
+                console.log('✅ ESM格式SDK成功初始化全局对象');
+                
+                // 绑定按钮事件
+                document.getElementById('test-esm-sdk').addEventListener('click', function() {
+                    console.log('测试ESM格式SDK功能');
+                    
+                    // 测试SDK实例
+                    if (window.monitorInstance) {
+                        console.log('SDK实例存在,版本信息:', window.monitorInstance.config);
+                        
+                        // 测试数据上报
+                        window.monitorInstance.reportData({
+                            type: 'esm_test_event',
+                            message: 'ESM格式SDK测试事件',
+                            timestamp: Date.now()
+                        });
+                    }
+                });
+                
+                document.getElementById('test-esm-functionality').addEventListener('click', function() {
+                    console.log('测试ESM格式SDK各项功能');
+                    
+                    // 测试错误上报
+                    try {
+                        throw new Error('ESM格式SDK测试错误');
+                    } catch(e) {
+                        window.monitorInstance.reportError({
+                            type: 'esm_test_error',
+                            message: e.message,
+                            stack: e.stack,
+                            timestamp: Date.now()
+                        });
+                    }
+                    
+                    // 测试性能数据
+                    window.monitorInstance.reportData({
+                        type: 'esm_performance_test',
+                        loadTime: 100,
+                        timestamp: Date.now()
+                    });
+                });
+            } else {
+                console.error('❌ ESM格式SDK未正确初始化全局对象');
+            }
+        }).catch(error => {
+            console.error('❌ 加载ESM格式的bundle时出错:', error);
+        });
+    </script>
+</body>
+</html>