在测试环境中落地 PageSpy 的实践记录

HuolalaTech/page-spy: 📦 The platform SDKs for PageSpy (github.com)

打破边界,PageSpy 新增重磅功能 - 掘金 (juejin.cn)

在看到 PageSpy 新增了 DataHarborPlugin 数据港口 插件后有觉得被直击了痛点

测试:你看这里有个 Bug,丢来一个截图

开发: 什么 Bug?! 在我这明明就是好的啊!!!你复现看看

测试:(复现不出)明明我刚刚就是有问题啊...

开发:这功能这么久了都这样,你懂不懂用啊,不懂就不要乱说,研发也很难的好吧

我们如何做的错误检测和回溯

我司前端(包括桌面浏览器端)主要使用 Uniapp进行开发,对接的是 UniApp 的 Uni 统计。在构建时输出 SourceMap 并上传至统计后台,应用发生错误即可将错误上报,在统计后台可以根据 SourceMap 定位到构建前的代码片段。

后端对每个请求都生成了 Request ID 并贯穿于整个请求链路,当后端抛出错误时响应中会携带 Request ID,同时将 Request ID 和错误堆栈写入日志。使用阿里云 SLS 日志平台对日志进行分析查询。

PageSpy 后对我们的改变

引入 PgaeSpy 之前,测试同学需要描述错误情况和所做的操作。有时甚至还需要附加 Console 控制台中的一些信息或后端接口返回的 Error ID 以辅助定位问题。(甚至有的时候测试同学的信息描述不全,研发还需要进一步询问具体的操作细节)

引入了 PageSpy 后借助 下载日志数据 功能,测试同学只需要描述错误情况,而不需要描述复现步骤和具体的页面操作情况。直接将日志发给开发,开发可以在 PageSpy 中进行日志回放。

我们的一些小修改

看似上面的流程已经比较方便了,但在我的使用过程中觉得在移动端进行下载日志数据的操作存在一些困难。

例如:某些应用的内置浏览器会提示需要使用外部浏览器打开才可以下载文件,而错误情况又于当前平台存在关联关系,又并且在外部浏览器中打开后日志文件就会丢失。。。

开发者工具中显示下载成功但是没有任何反应 / 安卓真机上提示需要在外部浏览器下载

查看文档后发现,在 DataHarborPlugin 中提供了一个 onDownload 参数,提供的入参就是客户端缓存的日志数据。

客户端可以使用传入的数据生成 Blob 文件,将文件通过接口上传给服务端。

经测试,如果将数据以 application/json 直接 POST 上传在网页中导入数据后会提示 JSON 解析失败。在客户端创建文件通过 FormData 上传即可正常解析。

typescript 复制代码
// 客户端
PageSpy.registerPlugin(
  new DataHarborPlugin({
    onDownload: async (data) => {
      const id = UUIDv4();

      const blob = new Blob([JSON.stringify(data)], {
        type: "application/json",
      });

      const formData = new FormData();
      formData.append("file", blob, `${id}.json`);

      await fetch("https://pagespy.example.com", {
        method: "POST",
        body: formData,
      }).then((res) => {
        if (res.ok) {
          alert(`日志已自动上报至服务器,请向开发提供错误 ID: ${id}`);
        } else {
          alert("日志上报错误,请重试");
        }
      });
    },
  }),
);
typescript 复制代码
// 服务端
const express = require('express');
const multer = require('multer');
const path = require('path');
const fs = require('fs');

const app = express();
const port = 6753;

// 设置 CORS 头部,允许所有来源的请求
app.use((req, res, next) => {
  res.header('Access-Control-Allow-Origin', '*');
  res.header('Access-Control-Allow-Headers', 'Origin, X-Requested-With, Content-Type, Accept');
  next();
});

// 配置 Multer 存储的目录和文件名
const storage = multer.diskStorage({
  destination: function (req, file, cb) {
    cb(null, 'data/');
  },
  filename: function (req, file, cb) {
    cb(null, file.originalname);
  }
});

const upload = multer({ storage: storage });

// POST 接口 /pagespy,处理文件上传
app.post('/pagespy', upload.single('file'), (req, res) => {
  if (req.file) {
    res.json({ message: 'File uploaded successfully', filename: req.file.originalname });
  } else {
    res.status(400).json({ error: 'No file uploaded' });
  }
});

app.listen(port, () => {
  console.log(`Server is running on http://localhost:${port}`);
});                              

之后的操作感觉就比较行了,测试可以告知开发错误 ID,开发在服务器上将日志文件下载回来回放即可。

相关推荐
java1234_小锋38 分钟前
【技术专题】HTML5 网页技术 - HTML5简介 & HTML5 文档结构
前端·html·html5
woniu_maggie1 小时前
SAP MDG主数据治理实战:从架构原理到项目实施全解析
后端
xiaoqiMikko1 小时前
Redis 实战(一):内存满了 —— 拒写、淘汰、被系统杀掉,以及删了 key 内存为什么不降(6.2.4 实测)
redis·后端
鶴哥只手遮天1 小时前
Vue 3 核心源码深度剖析系列(v3.5.44)-第 1 章 项目全景:monorepo 架构与工程化体系
前端·vue.js·开源
流星。。方1 小时前
小团队官网SEO落地:前端语义化与静态生成的工程实践
前端·状态模式
用户530429765791 小时前
盘点危化品搬运诊断的6类工具与自处理边界判断
前端
curtain1 小时前
从古法编程到 Agent:我入行这两年,AI 改变了什么
前端·openai
工程师小爱1 小时前
电芯尺寸合格,不等于电池包尺寸合格
后端
zyfts1 小时前
10分钟自制Codex钉钉通知Skill:AI干完活自动钉钉提醒你
前端