美文网首页
如何记录前端再用户浏览器上发生的错误并汇报给服务器?

如何记录前端再用户浏览器上发生的错误并汇报给服务器?

作者: 威少带我砍三双 | 来源:发表于2021-03-22 10:34 被阅读0次

一、代码执行的错误捕获1.try......catch

1.使用try... catch包裹,影响代码可读性。无法处理异步中的错误无法处理语法错误

try{
//可能出现异常的代码
}catch(异常类型  变量名){
//处理异常的代码
}finally{
//无论try块中是否有异常,均实现的代码
}
2.window.onerrorwindow.onerror

比try catch要强那么一丢丢。无论是异步还是非异步错误,onerror都能捕获到运行时错误
缺点:监听不到资源加载的报错onerror,事件处理函数只能声明—次,不会重复执行多个回调:
window.onerror是一个全局变量,默认值为null。当有js运行时错误触发时,window会触发error事件,并执行window.onerror()。onerror可以接受多个参数。

window.onerror = function(message, source, lineno, colno, error) { ... }
 
函数参数:
 
*   message:错误信息(字符串)。可用于HTML onerror=""处理程序中的event。
*   source:发生错误的脚本URL(字符串)
*   lineno:发生错误的行号(数字)
*   colno:发生错误的列号(数字)
*   error:Error对象
 
若该函数返回true,则阻止执行默认事件处理函数,如异常信息不会在console中打印。没有返回值或者返回值为false的时候,异常信息会在console中打印
3.window.addEventListener('error')

可以监听到资源加载报错,也可以注册多个事件处理函数。
监听js运行时错误事件,会比window.onerror先触发,与onerror的功能大体类似,不过事件回调函数传参只有一个保存所有错误信息的参数,不能阻止默认事件处理函数的执行,但可以全局捕获资源加载异常的错误

window.addEventListener('error', function(event) { ... })
 
当资源(如img或script)加载失败,加载资源的元素会触发一个Event接口的error事件,并执行该元素上的onerror()处理函数。这些error事件不会向上冒泡到window,但可以在捕获阶段被捕获
因此如果要全局监听资源加载错误,需要在捕获阶段捕获事件
//图片加载失败使用默认图片,依旧加载失败超过三次使用base64图片
window.addEventListener('error',function(e){
    let target = e.target, // 当前dom节点
        tagName = target.tagName,
        count = Number(target.dataset.count ) || 0, // 以失败的次数,默认为0
        max= 3; // 总失败次数,此时设定为3
    // 当前异常是由图片加载异常引起的
    if( tagName.toUpperCase() === 'IMG' ){
        if(count >= max){
            target.src = 'data:image/jpeg;base64,/9j/4AAQSkZJRgABAQEAYABgAAD//AK3/ALYH+5hX6FV5N4Y/5GHwx/vyf+iJa9ZrysPhoYVShDZu/potDmwWFhhIzhT2bv6aLQ//Z';
        }else{
            target.dataset.count = count + 1;
            target.src = '//xxx/default.jpg';
        }
    }
},true)
4.window.addEventListener("'unhandledrejection')

捕获未处理的promise异常与错误
使用Promise编写异步代码时,使用reject来处理错误。有时,开发者通常会忽略这一点,导致一些错误没有得到处理。例如:

function main() {
    asyncFunc()
    .then(···)
    .then(() => console.log('Done!'));
}

由于没有使用catch方法捕获错误,当asyncFunc()函数reject时,抛出的错误则没有被处理。

浏览器中未处理的Promise错误
一些浏览器(例如Chrome)能够捕获未处理的Promise错误。

。unhandledrejection
监听unhandledrejection事件,即可捕获到未处理的Promise错误:
。reason: Promise的reject值

window.addEventListener('unhandledrejection', event => {
    console.log(event.reason); // Hello, Fundebug!
});
function foo() {
    Promise.reject('Hello, Fundebug!');
}
foo();

当一个Promise错误最初未被处理,但是稍后又得到了处理,则会触发rejectionhandled事件

window.addEventListener('unhandledrejection', event =>
{
    console.log(event.reason); // 打印"Unhandle Promise Error!"
});
 
window.addEventListener('rejectionhandled', event => {
    console.log('rejection handled'); // 1秒后打印"rejection handled"
});
 
function foo() {
    return Promise.reject('Unhandle Promise Error!');
}
 
var r = foo();
 
setTimeout(() => {
    r.catch(e =>{});
}, 1000);

二、资源加载的错误捕获

1. imgObj.onerror()

大家上网的时候肯定见到过加载失败的红叉图片,具体如下图。当然现在Google Chrome与Firefox对其处理会好看一些。

image

其实可以利用<img>图片标签的onerror事件对其处理的,要求其加载失败之后,马上加载一张默认图片,而不是显示为红叉叉。

其代码如下:

<img src="s.png" onerror="javascript:this.src='xx.png';this.width=80;this.height=80;" />  

意为,如果加载s.png这张图片失败了,就马上去加载xx.png这张图片,同时xx.png这张图片要求其以80x80的方式加载。

2. performance.getEntries),获取到成功加载的资源,对比可以间接的捕获错误

浏览器获取网页时,会对网页中每一个对象(脚本文件、样式表、图片文件等等)发出一个HTTP请求。而通过window.performance.getEntries方法,则可以以数组形式,返回这些请求的时间统计信息,每个数组成员均是一个PerformanceResourceTiming对象!

用它小玩儿一下,统计页面上的静态资源加载耗时:

(function () {
    // 浏览器不支持,就算了!
    if (!window.performance && !window.performance.getEntries) {
        return false;
    }

    var result = [];
    // 获取当前页面所有请求对应的PerformanceResourceTiming对象进行分析
    window.performance.getEntries().forEach(function (perf) {
        result.push({
            'url': perf.name,
            'entryType': perf.entryType,
            'type': perf.initiatorType,
            'duration(ms)': perf.duration
        });
    });

    // 控制台输出统计结果
    console.table(result);
})();
image.png
  1. window.addEventListener('error', fn, true),会捕获但是不冒泡,所以window.onerror不会触发,捕获阶段可以触发 上面已经有示例代码
    三、错误上报
    —般使用image来上报,用请求图片的方式来上报信息问题;
    使用图片发送get请求,上报信息,由于浏览器对图片有缓存,同样的请求,图片只会发送一次,避免重复上报。
    例: 和请求ajax的方式一样
<script>
(new Image()).src="http://www.baidu.com?n=fff"
</script>

首先创建一个图片,将其src属性设置为

http://www.baidu.com?n=fff

后期的参数就是需要上报的错误了,可以直接在network中查看参数,类似于ajax请求.


image.png

四、借助第三方库
o sentry-javascript

相关文章

  • 如何记录前端再用户浏览器上发生的错误并汇报给服务器?

    一、代码执行的错误捕获1.try......catch 1.使用try... catch包裹,影响代码可读性。无法...

  • 前端错误

    这里所说的前端错误是指,在用户的浏览器中出现的js报错。如下图。 此类错误有几个特征: 报错信息一般发生在浏览器控...

  • 面试题(二)

    1、如何理解前端? 前端即网站前台部分,也叫前端开发,运行在PC端,移动端等浏览器上展现给用户浏览的网页。 2、H...

  • 前端发展个人梳理

      前端的本质就是展示数据给用户,最原始的前端工作就是从服务器获取html文档,然后渲染展示在浏览器上面。随着互联...

  • 2017.11.01

    前端:运行在用户的浏览器上 后台:运行在服务器上 node 1 火爆 2 语法就是js语法 3性能非...

  • HTTP Cookies知识-查看、发送、获取、返回

    1 简介 HTTP Cookies是服务器发送到用户浏览器并保存在本地的一小块数据,它会在浏览器下次向同一服务器再...

  • 前端简介--HTML与CSS

    一. 了解前端 1. 什么是前端 前端即网站前台部分,运行在PC端,移动端等浏览器上展现给用户浏览的网页。随着互联...

  • 前端知识(Html)汇总1

    一. 了解前端 1. 什么是前端 前端即网站前台部分,运行在PC端,移动端等浏览器上展现给用户浏览的网页。随着互联...

  • 001 前端概述

    前端 一、什么是前端 ​ 前端即网站前台部分,运行在PC端,移动端等浏览器上展现给用户浏览的网页。随着互联网技...

  • WebView之Cookies

    Cookie 是服务器发送到用户浏览器并保存在浏览器上的一块数据,它会在浏览器下一次发起请求时被携带并发送到服务器...

网友评论

      本文标题:如何记录前端再用户浏览器上发生的错误并汇报给服务器?

      本文链接:https://www.haomeiwen.com/subject/jptzcltx.html