用window.onerror捕获并上报Js错误的方法


Posted in Javascript onJanuary 27, 2016

前两天有个2048游戏的用户反馈说,打开游戏后不能玩儿,只有一个游戏面板,数字无法初始化,更无法移动,设备为iPhone 4S、iOS 5.1。尝试从微信调起Safari打开,依然不好使。由于游戏中运用了比较多的HTML5特性,所以粗略估计是有JS报错导致。不过这样的信息该如何捕获到呢?当然是传说中的window.onerror。

从W3C找到关于window.onerror的方法体介绍:

用window.onerror捕获并上报Js错误的方法

这个意思,基本可以就是说,window.onerror方法,我们可以写成:

/** 
 * @param {String} errorMessage  错误信息 
 * @param {String} scriptURI   出错的文件 
 * @param {Long}  lineNumber   出错代码的行号 
 * @param {Long}  columnNumber  出错代码的列号 
 * @param {Object} errorObj    错误的详细信息,Anything 
 */
window.onerror = function(errorMessage, scriptURI, lineNumber,columnNumber,errorObj) { 
  // TODO 
}

不过使用过程中还得注意兼容性问题,不是所有浏览器都有参数列表中的所有参数,chrome之类的,都是浏览器标准草案的领跑者,这些个参数用就是了!

于是,可以写一个小Demo来尝试一下:

<!DOCTYPE html> 
<html> 
<head> 
  <title>Js错误捕获</title> 
  <script type="text/javascript"> 
  /** 
   * @param {String} errorMessage  错误信息 
   * @param {String} scriptURI   出错的文件 
   * @param {Long}  lineNumber   出错代码的行号 
   * @param {Long}  columnNumber  出错代码的列号 
   * @param {Object} errorObj    错误的详细信息,Anything 
   */ 
  window.onerror = function(errorMessage, scriptURI, lineNumber,columnNumber,errorObj) { 
    console.log("错误信息:" , errorMessage); 
    console.log("出错文件:" , scriptURI); 
    console.log("出错行号:" , lineNumber); 
    console.log("出错列号:" , columnNumber); 
    console.log("错误详情:" , errorObj); 
  } 
  </script> 
</head> 
<body> 
  <script type="text/javascript" src="error.js"></script> 
</body> 
</html>

其中error.js文件中的内容,简单的这样写一句:

throw new Error("出错了!");
用浏览器跑起来以后,打开console,基本就是这样的了:

用window.onerror捕获并上报Js错误的方法

所以,这些数据都是可以做上报的了。
当然了,上面的error.js是和html页面同域名下,如果error.js不在同域下,会是怎样的?我们把error.js的引用改一下:

<script type="text/javascript" src="//doitbegin.duapp.com/error.js"></script>
再来打开console,我们看到的是这样的:

用window.onerror捕获并上报Js错误的方法

相当于window.onerror方法只捕获到了一个errorMessage,而且是固定字符串,毫无参考价值。查了点资料(Webkit源码),发现在浏览器实现script资源加载的地方,是进行了同源策略判断的,如果是非同源资源,errorMessage就被写死为“Script error”了:

用window.onerror捕获并上报Js错误的方法

好在script标签有一个crossorigin属性,设置它可以显示比较详细的错误信息,我们试着将script标签改一下:

<script type="text/javascript" src="//doitbegin.duapp.com/error.js" crossorigin></script>
刷新页面,这个时候看到console中的输出是这样的:

用window.onerror捕获并上报Js错误的方法

出现这个error也不意外,既然设置了error.js为crossorigin,那error.js的HTTP Response Header也必须设置非同源可访问。为了方便设置Header,把error.js做一个小改动,更名为:error-js.php。

<?php 
  header('Access-Control-Allow-Origin:*'); 
  header('Content-type:text/javascript'); 
?> 
throw new Error('出错了');

此时刷新页面,看到console中的输出就已经正常了,所有信息都能正常捕获:

用window.onerror捕获并上报Js错误的方法

OK,技术细节分析结束!我2048游戏静态资源是放到静态域(非同源)下的,所以要想通过window.onerror捕获错误信息,就得按照上面的最后一种情况来操作了:

1、添加script的crossorigin属性

2、配置一下服务器,设置静态资源Javascript的Response为Access-Control-Allow-Origin

Javascript 相关文章推荐
解析JavaScript中instanceof对于不同的构造器或许都返回true
Dec 03 Javascript
SyntaxHighlighter 3.0.83使用笔记
Jan 26 Javascript
Javascript发送AJAX请求实例代码
Aug 21 Javascript
vuex实现简易计数器
Oct 27 Javascript
基于jQuery实现Accordion手风琴自定义插件
Oct 13 Javascript
使用ionic播放轮询广告的实现方法(必看)
Apr 24 Javascript
《javascript少儿编程》location术语总结
May 27 Javascript
vue 点击展开显示更多(点击收起部分隐藏)
Apr 09 Javascript
详解Webpack如何引入CDN链接来优化编译后的体积
Jun 21 Javascript
vue 解除鼠标的监听事件的方法
Nov 13 Javascript
详解Vue的ref特性的使用
Jan 24 Javascript
详解datagrid使用方法(重要)
Nov 06 Javascript
jquery实现可旋转可拖拽的文字效果代码
Jan 27 #Javascript
jquery+css3实现会动的小圆圈效果
Jan 27 #Javascript
再谈JavaScript异步编程
Jan 27 #Javascript
简单介绍jsonp 使用小结
Jan 27 #Javascript
理解javascript异步编程
Jan 27 #Javascript
js实现的鼠标滚轮滚动切换页面效果(类似360默认页面滚动切换效果)
Jan 27 #Javascript
AngularJS转换响应内容
Jan 27 #Javascript
You might like
php MsSql server时遇到的中文编码问题
2009/06/11 PHP
利用PHP实现图片等比例放大和缩小的方法详解
2013/06/06 PHP
php操纵mysqli数据库的实现方法
2016/09/18 PHP
yii2 commands模式以及配置crontab定时任务的方法
2017/08/19 PHP
关于恒等于(===)和非恒等于(!==)
2007/08/20 Javascript
javascript 实现简单的table排序及table操作练习
2012/12/28 Javascript
Js数组的操作push,pop,shift,unshift等方法详细介绍
2012/12/28 Javascript
javascript定义变量时加var与不加var的区别
2014/12/22 Javascript
JavaScrip调试技巧之断点调试
2015/10/22 Javascript
javascript实现仿百度图片的瀑布流加载效果
2016/04/20 Javascript
全面理解JavaScript中的继承(必看)
2016/06/16 Javascript
Vue.js常用指令之循环使用v-for指令教程
2017/06/27 Javascript
jfinal与bootstrap的登出实战详解
2017/11/27 Javascript
vue使用iframe嵌入网页的示例代码
2020/06/09 Javascript
jQuery实现获取当前鼠标位置并输出功能示例
2019/01/05 jQuery
JS数组中对象去重操作示例
2019/06/04 Javascript
Vue-CLI项目中路由传参的方式详解
2019/09/01 Javascript
为nuxt项目写一个面包屑cli工具实现自动生成页面与面包屑配置
2019/09/29 Javascript
[05:40]DOTA2荣耀之路6:Wings最后进攻
2018/05/30 DOTA
简单介绍Python下自己编写web框架的一些要点
2015/04/29 Python
python切片(获取一个子列表(数组))详解
2019/08/09 Python
详解PyQt5中textBrowser显示print语句输出的简单方法
2020/08/07 Python
Django 权限管理(permissions)与用户组(group)详解
2020/11/30 Python
Dillard’s百货官网:Dillards.com
2018/05/26 全球购物
意大利宠物用品购物网站:Bauzaar
2018/09/15 全球购物
Juicy Couture Beauty官方网站:香水和化妆品
2019/03/12 全球购物
戴尔马来西亚官网:Dell Malaysia
2020/05/02 全球购物
入党政审材料范文
2014/12/24 职场文书
先进个人事迹材料
2014/12/29 职场文书
黄石寨导游词
2015/02/05 职场文书
2015年老干部工作总结
2015/04/23 职场文书
乔布斯辞职信(中英文对照)
2015/05/12 职场文书
运动会开幕式通讯稿
2015/07/18 职场文书
《珍珠鸟》教学反思
2016/02/16 职场文书
浅谈node.js中间件有哪些类型
2021/04/29 Javascript
css position fixed 左右双定位的实现代码
2021/04/29 HTML / CSS