最强前端测试教程 4 通过测试来做性能分析

559 阅读2分钟

前言

经过本系列之前的教程我们已经可以跑起来一个集成测试了,如果团队践行了这个实践,那么项目一定是坚不可摧的。但是又引发出了另一个问题,就是如果测试数量庞大,几千几万个case,每次 mr 跑一遍是很耗时的,这时候就需要有人来研究测试慢的原因了,进行 debug,profile 等。找出慢的测试同时也能帮我们定位有问题的代码,下面我来教你们怎么通过测试代码进行性能分析

step 1: 新建 profile.ts

代码如下

import fs from 'fs'
import { Session } from 'inspector'
import path from 'path'

let session: Session

export async function startProfiling() {
    session = new Session()
    session.connect()
    await new Promise((f) => {
        session.post('Profiler.enable', () => {
            session.post('Profiler.start', f)
        })
    })
}

export async function stopProfiling(profileName = 'integration-test') {
    await new Promise((f) =>
        session.post('Profiler.stop', (err, res) => {
            if (!err) {
                const targetPath = path.join(__dirname, profileName + '.json')

                fs.writeFileSync(targetPath, JSON.stringify(res.profile))
            }
            f(1)
        })
    )
}

我们使用的 nodejs 的 inspector,这是一个强大的内置调试工具,它可以连接到 chrome devtool 对 nodejs 进行调试。那么就说明他一定有方法导出 profile。于是看了一下类型定义,果然发现了一个接口

image.png 那么我们就直接在测试的开始和结束的时候调用一下就行了,然后把记录的内容新建一个文件导出来。

step 2: 模拟一个慢操作

我们找到一个地方加点 hack 的代码,比如在点击收藏按钮的时候创建 3000 个 div

image.png

step 3: 在测试中开启记录 profile

在测试代码中添加如下命令

// ...
beforeAll(async () => {
    await startProfiling()
})
afterAll(async () => {
    await stopProfiling()
})
// ...

然后运行测试npm run test后可以看到新增了一个文件

image.png

step 4: 把生成的 profile 给拖到 chrome性能面板中进行查看

image.png 点击 自上而下

image.png 可以看到最耗时的操作appendChil暴露出来了, 继续展开看一下

image.png

定位到前面写的 mockSlow 了。🎉

结尾

可能有人会问,我明明自己录制调试一下也可以发现,为什么要折腾这么一圈? 这其实就是测试的好处了,因为大部分情况,人们不知道自己的代码有问题,比如 100ms 200ms 的延迟察觉不到,比如本应该是全局单例结果实例数量会随着页面跳转而增加。这些问题通常会被“我这跑起来没问题啊”这种话给忽略掉。但是未来你可能就要被页面卡死或者内存泄露的 bug 折磨一整天。通过观察测试运行的时间变化,内存变化可以及时定位这些问题,除掉隐患。