You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用Puppeteer模拟浏览器崩溃并触发disconnected事件?

问题

我用Jest和Puppeteer运行大量测试,为避免复用浏览器导致不稳定,每次测试前都会通过puppeteer.launch()创建新的浏览器实例。批量运行所有测试时,浏览器偶尔会在启动后崩溃,我可以通过监听browser.on('disconnected', ...)事件检测到这种情况。

现在我想处理该场景,在需要时重新创建浏览器,但问题是如何强制Chromium浏览器崩溃并触发与真实崩溃相同的disconnected事件?我已尝试加载chrome://kill/这类特殊URL,示例代码如下:

import puppeteer from 'puppeteer';

async function getPage(url) {
  const browser = await puppeteer.launch({});
  const page = await browser.newPage();
  browser.on('disconnected', async () => {
    console.log('@@@@@@@@@@@@ browser crashed @@@@@@@@@@@@@');
  });
  await page.goto(url, {waitUntil: 'load'});
  return page;
};

describe('Raw Puppeteer Test', () => {
  let page;
  beforeEach(async () => {
    page = await getPage('chrome://kill/');
  });
  afterEach(async () => {
    await page.close();
    await page.browser().close();
  });
  it('should relaunch the browser and re-run if the browser crashes', async () => {
    const el = await page.waitForSelector('h1');
    expect(el).not.toBeNull();
  });
});

虽然chrome://kill/和chrome://crash/确实会导致Chromium崩溃,但不会触发真实崩溃时的disconnected事件;尝试chrome://inducebrowsercrashforrealz/则返回net::ERR_INVALID_URL错误。

有没有办法在Puppeteer中模拟浏览器初始化失败或真实崩溃场景,触发对应的disconnected事件?


解决方案

方法1:直接终止浏览器进程

通过browser.process()获取Chromium的进程实例,调用kill()方法强制终止,这会直接触发disconnected事件,和真实崩溃的效果一致:

async function simulateBrowserCrash(browser) {
  if (browser.process()) {
    browser.process().kill('SIGKILL'); // 强制终止进程
  }
}

// 在测试中使用示例
beforeEach(async () => {
  const browser = await puppeteer.launch({});
  const page = await browser.newPage();
  browser.on('disconnected', () => {
    console.log('浏览器已崩溃/断开连接');
  });
  
  // 触发模拟崩溃
  await simulateBrowserCrash(browser);
});

方法2:通过Chrome DevTools协议强制崩溃

使用Puppeteer的browser.send()方法发送Chrome DevTools协议的Browser.crash命令,这会让浏览器主动崩溃并触发disconnected事件:

async function simulateBrowserCrash(browser) {
  await browser.send('Browser.crash');
}

// 使用示例
async function getPage() {
  const browser = await puppeteer.launch({});
  const page = await browser.newPage();
  browser.on('disconnected', () => {
    console.log('@@@@@@@@@@@@ browser crashed @@@@@@@@@@@@@');
  });
  
  // 触发模拟崩溃
  await simulateBrowserCrash(browser);
  return page;
}

方法3:模拟浏览器初始化失败

如果要测试浏览器启动阶段的失败场景,可以修改puppeteer.launch()的参数,让浏览器无法正常启动:

// 指定无效的用户数据目录,导致启动失败
async function simulateLaunchFailure() {
  try {
    const browser = await puppeteer.launch({
      userDataDir: '/path/that/does/not/exist/and/cannot/be/created',
      args: ['--no-sandbox'] // 根据运行环境调整参数
    });
  } catch (error) {
    console.log('浏览器初始化失败:', error.message);
    // 此处可加入重试逻辑
  }
}

内容的提问来源于stack exchange,提问作者antun

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.17 12:10:38