VUE前端工程报错监控问题及解决

 更新时间:2026年04月25日 10:12:22   作者:pobu168  
文章介绍了在Vue3项目中实现错误捕获和邮件报错上报的方法,首先使用了`errorHandler`全局错误捕获,接着通过Nodemailer发送邮件实现错误上报功能,过程中遇到一些坑,如需本地调试需用node启动服务,同时总结了两种方案的,包括直接存在的问题和限制

故事的开始

作为前端,有没有一种冲动,希望在代码出问题时能前人一步收到报错的信息,而不是被用户发现后再反馈上来。

如果要做到提前收到报错信息,至少需要做到两点:

  1. 错误捕获
  2. 错误信息上报

错误捕获

以vue3提供了errorHandler

指定一个处理函数,来处理组件渲染函数和 侦 听 器 执行期间抛出的未捕获错误。这个处理函数被调用时,可获取错误信息和相应的应用实例。

main.ts 中设置全局错误捕获

app.config.errorHandler = (err, vm, info) => {
  console.log('[全局异常]', err, vm, info)
}

人为制造了点报错:

[全局异常] ReferenceError: www is not defined
    at asset-mgmt.vue:241:15
    at callWithErrorHandling (runtime-core.esm-bundler.js:155:22)
    at callWithAsyncErrorHandling (runtime-core.esm-bundler.js:164:21)
    at hook.__weh.hook.__weh (runtime-core.esm-bundler.js:2667:29)
    at flushPostFlushCbs (runtime-core.esm-bundler.js:356:32)
    at flushJobs (runtime-core.esm-bundler.js:401:9) VueInstance mounted hook

如此,便实现了错误的捕获。

错误信息上报

上报的方式很多,此处单说通过邮件方式实现上报

邮件方式实现大致分为两种:

  • 通过接口调用后台邮件服务实现
  • 前端独立实现发送邮件功能

本着自己的事情自己做的原则,接下来前端独立实现邮件的发送功能

Nodemailer

首先进入视线的是Nodemailer

Nodemailer 是一个简单易用的 Node.JS 邮件发送模块(通过 SMTP,sendmail,或者 Amazon SES),支持 unicode,你可以使用任何你喜欢的字符集。

测试代码如下:

/* eslint no-console: 0 */

'use strict';

const nodemailer = require('nodemailer');

// Generate SMTP service account from ethereal.email
nodemailer.createTestAccount((err, account) => {
    if (err) {
        console.error('Failed to create a testing account');
        console.error(err);
        return process.exit(1);
    }
    console.log('Credentials obtained, sending message...');

    let transporter = nodemailer.createTransport(
      
        {
            host: "smtp.qq.com",
            port: 465,
            secure: true, // true for 465, false for other ports
            auth: {
              user: "xxxxx@qq.com", //  邮箱地址
              pass: "tkelxjoezeatbjee", //授权码
            },
            logger: true,
            transactionLog: true // include SMTP traffic in the logs
        },
        {
            // sender info
            from: 'Nodemailer <xxxxx@qq.com>',
            headers: {
                'X-Laziness-level': 1000 // just an example header, no need to use this
            }
        }
    );

    // Message object
    let message = {
        // Comma separated list of recipients
        to: 'xxxxx@qq.com',

        // Subject of the message
        subject: 'Nodemailer is unicode friendly ✔' + Date.now(),

        // plaintext body
        text: 'Hello to myself!',

        // HTML body
        html: ``,

        // AMP4EMAIL
        amp: `134253647`,

        // An array of attachments
        attachments: [],

        list: {}
    };

    transporter.sendMail(message, (error, info) => {
        if (error) {
            console.log('Error occurred');
            console.log(error.message);
            return process.exit(1);
        }
        console.log('Message sent successfully!');
        console.log(nodemailer.getTestMessageUrl(info));

        // only needed when using pooled connections
        transporter.close();
    });
});

上述功能是配置了QQ邮箱给自己发邮件:

[2022-06-17 08:32:05] DEBUG Creating transport: nodemailer (6.7.5; +https://nodemailer.com/; SMTP/6.7.5[client:6.7.5])
[2022-06-17 08:32:05] DEBUG Sending mail using SMTP/6.7.5[client:6.7.5]
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] Resolved smtp.qq.com as 14.18.175.202 [cache miss]
[2022-06-17 08:32:05] INFO  [hvJt01jlQc8] Secure connection established to 14.18.175.202:465
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] S: 220 newxmesmtplogicsvrsza7.qq.com XMail Esmtp QQ Mail Server.
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] C: EHLO fengjingyudeMacBook-Pro-2.local
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] S: 250-newxmesmtplogicsvrsza7.qq.com
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] S: 250-PIPELINING
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] S: 250-SIZE 73400320
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] S: 250-AUTH LOGIN PLAIN XOAUTH XOAUTH2
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] S: 250-AUTH=LOGIN
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] S: 250-MAILCOMPRESS
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] S: 250 8BITMIME
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] SMTP handshake finished
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] C: AUTH PLAIN ADI0NDIwMjk2OUBxcS5jb20ALyogc2VjcmV0ICov
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] S: 235 Authentication successful
[2022-06-17 08:32:05] INFO  [hvJt01jlQc8] User "xxxxx@qq.com" authenticated
[2022-06-17 08:32:05] INFO  Sending message <93f13de6-5a1e-bd6f-24e0-8608d5442c93@qq.com> to <xxxxx@qq.com>
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] C: MAIL FROM:<xxxxx@qq.com>
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] S: 250 OK
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] C: RCPT TO:<xxxxx@qq.com>
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] S: 250 OK
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] C: DATA
[2022-06-17 08:32:05] DEBUG [hvJt01jlQc8] S: 354 End data with <CR><LF>.<CR><LF>.
[2022-06-17 08:32:05] INFO  [hvJt01jlQc8] <668 bytes encoded mime message (source size 665 bytes)>
[2022-06-17 08:32:06] DEBUG [hvJt01jlQc8] S: 250 OK: queued as.
[2022-06-17 08:32:06] DEBUG [hvJt01jlQc8] Closing connection to the server using "end"
Message sent successfully!
[2022-06-17 08:32:06] INFO  [hvJt01jlQc8] Connection closed

如此,便实现了发邮件的功能,将捕获的错误信息写入邮件内容就可以实现上报了。

这里有坑不知道你会不会遇到:

  1. 这是个node服务、node服务、node服务,要用node命令启动。在这个位置卡住了一段,傻傻的以为可以用js直接调用。这里延伸出一个问题,需要事先启动该服务,以便上报时调用
  2. 如下配置中的邮箱需要是相同的邮箱,想来简单,但就是卡了我一下

Formspree

如果node服务都不想起,那Formspree是个选择。

过程大致是如下:

  1. 注册登录Formspree
  2. 配置接受信息的邮箱,并验证邮箱

3、配置一个接收信息的form,会生成一个链接,即为调用的地址

https://formspree.io/f/xvolyepj

​ 说下遇到的问题:

  • form名称在新增时保证正确,修改名称虽成功,但影响接收
  • form的内容不影响数据的传递,数据的字段可以在调用是指定,可与设置时无关

4、调用

app.config.errorHandler = (err, vm, info) => {
  console.log('[全局异常]', err, vm, info)
  axios({
    method: 'post',
    url: 'https://formspree.io/f/xvolyepj',
    data: {
      errorMsg: err.message,
      errorDetail: err.stack,
      sss: '44444'
    }
  })
}

5、结果

除掉邮箱需要托管之外,也算是个不错的方案。但是……

万事怎么可能没有但是,测试到后面收到个邮件,才发现是有限额的,两个邮箱,每月50 条,土豪请办卡。

6、后续

上述两种邮件通知方案都存在一致命的缺陷,就是在内网环境下可能无法实现上述所需网络环境的联通,造成功能不可以。

总结

以上为个人经验,希望能给大家一个参考,也希望大家多多支持脚本之家。

相关文章

  • 如何去掉el-table中自带的边框线

    如何去掉el-table中自带的边框线

    文章介绍了如何去掉Element UI中el-table组件自带的边框线,通常情况下,el-table没有添加border属性,但仍然会出现边框线,可能的原因包括ElementUI的默认样式或表格的某些内置样式,感兴趣的朋友跟随小编一起看看吧
    2025-01-01
  • Vue3+Vite实现项目搭建步骤

    Vue3+Vite实现项目搭建步骤

    这篇文章主要介绍了Vue3+Vite实现项目搭建步骤,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2024-07-07
  • 详解如何在Vue3中实现懒加载组件

    详解如何在Vue3中实现懒加载组件

    随着现代前端框架的发展,懒加载作为一种优秀的性能优化技术,在用户体验和加载速度上扮演着越来越重要的角色,本文将详细介绍如何在 Vue 3 中实现懒加载组件,确保你能够将这一技术应用到自己的项目中,需要的朋友可以参考下
    2024-11-11
  • vue中引入高德地图并多点标注的实现步骤

    vue中引入高德地图并多点标注的实现步骤

    这篇文章主要介绍了vue中引入高德地图并多点标注,实现步骤是通过vue的方法引入地图,初始化地图,设置宽和高,本文通过实例代码给大家介绍的非常详细,需要的朋友可以参考下
    2022-09-09
  • Vue Vuex搭建vuex环境及vuex求和案例分享

    Vue Vuex搭建vuex环境及vuex求和案例分享

    这篇文章主要介绍了Vue Vuex搭建vuex环境及vuex求和案例分享, Vue 中实现集中式状态管理的一个 Vue 插件,对 vue 应用中多个组件的共享状态进行集中式的管理,下文相关介绍,需要的朋友可以参考一下
    2022-04-04
  • Vue+EleMentUI实现el-table-colum表格select下拉框可编辑功能实例

    Vue+EleMentUI实现el-table-colum表格select下拉框可编辑功能实例

    这篇文章主要给大家介绍了关于Vue+EleMentUI实现el-table-colum表格select下拉框可编辑功能的相关资料,element-UI表格的使用相信大家都不陌生,文中给出了详细的代码示例,需要的朋友可以参考下
    2023-07-07
  • vue axios数据请求get、post方法及实例详解

    vue axios数据请求get、post方法及实例详解

    axios是一个基于Promise,同时支持浏览器端和Node.js的HTTP库,常用于Ajax请求。这篇文章主要介绍了vue axios数据请求get、post方法的使用 ,需要的朋友可以参考下
    2018-09-09
  • vue中调接口的方式详解this.$api、直接调用、axios

    vue中调接口的方式详解this.$api、直接调用、axios

    这篇文章主要介绍了vue中调接口的方式:this.$api、直接调用、axios,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2023-11-11
  • vue使用vuex实现首页导航切换不同路由的方法

    vue使用vuex实现首页导航切换不同路由的方法

    这篇文章主要介绍了vue使用vuex实现首页导航切换不同路由的方法 ,非常不错,具有一定的参考借鉴价值,需要的朋友可以参考下
    2019-05-05
  • Vuex 进阶之模块化组织详解

    Vuex 进阶之模块化组织详解

    这篇文章主要介绍了Vuex 进阶之模块化组织详解,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2018-01-01

最新评论