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

Linux CI环境构建Chrome扩展时遇backgroundPage获取超时问题

问题排查与修复方案

核心问题分析

  1. 无头模式配置冲突:代码同时设置headless: false和args: ['--headless=new'],导致浏览器启动模式混乱。本地Mac环境可能兼容这种冲突,但Linux CI环境会严格遵循命令行参数,引发扩展加载逻辑异常。
  2. 硬等待不可靠:setTimeout(3000)的固定等待时间无法适配CI环境的资源波动,扩展背景页可能未初始化完成就执行后续逻辑。
  3. 事件监听后未更新变量:调用waitForEvent('backgroundpage')后,未将返回的新背景页赋值给background变量,后续仍使用初始空值,导致获取extensionId失败。
  4. 路径与构建完整性:CI环境下扩展构建产物路径可能与本地不一致,或构建过程存在缓存、权限问题,导致加载的扩展不完整。

具体修复步骤

1. 修正无头模式配置

移除headless: false,统一使用--headless=new参数,确保浏览器启动模式一致:

const context = await chromium.launchPersistentContext('', {
  args: [
    '--headless=new',
    `--disable-extensions-except=${pathToExtension}`,
    `--load-extension=${pathToExtension}`
  ]
});

2. 替换硬等待为事件驱动逻辑

去掉固定setTimeout,改用waitForEvent直接等待背景页就绪,避免依赖不可靠的时间预估:

// 等待背景页事件触发,直接获取有效页面实例
const background = await context.waitForEvent('backgroundpage', { timeout: 300000 });

3. 优化背景页获取逻辑

直接通过事件监听获取背景页,无需先判断context.backgroundPages()——CI环境下初始调用可能返回空数组:

try {
  const background = await context.waitForEvent('backgroundpage', { timeout: 300000 });
  const extensionId = background.url().split('/')[2];
  console.log('Extension ID:', extensionId);
  testInfo.context = context;
  testInfo.extensionId = extensionId;
} catch (error) {
  console.error('Error occurred while getting the extension ID:', error);
} finally {
  await context.close(); // 无论成败都关闭上下文,避免资源泄漏
}

4. 验证CI环境下的扩展路径与构建完整性

  • 在代码中打印扩展路径,确认CI环境下路径正确:
    console.log('Loading extension from:', pathToExtension);
    
  • 构建扩展时添加--clean参数,避免CI缓存旧产物:
    const command = 'yarn workspace @akeyless/ztwa-extension build:prod --clean';
    
  • 检查CI环境下扩展构建产物的权限,确保Chromium有权限读取目录文件。

5. 添加CI适配参数

针对Linux CI环境,添加Chromium兼容性参数,避免沙箱或资源限制问题:

args: [
  '--headless=new',
  `--disable-extensions-except=${pathToExtension}`,
  `--load-extension=${pathToExtension}`,
  '--no-sandbox',
  '--disable-setuid-sandbox',
  '--disable-dev-shm-usage'
]

完整修复后的代码示例

import { chromium, BrowserContext } from '@playwright/test';
import path from 'path';
import { automationPath } from 'automation/applications/common/path';
import { execSync } from 'child_process';

interface TestInfo {
  context: BrowserContext;
  extensionId: string;
}

export default async ({}, testInfo: TestInfo) => {
  testInfo = testInfo || {};
  const command = 'yarn workspace @akeyless/ztwa-extension build:prod --clean';
  execSync(command, { encoding: 'utf-8', maxBuffer: 1000 * 10000 * 100 });

  const pathToExtension = path.join(__dirname, automationPath.extension);
  console.log('Loading extension from:', pathToExtension);

  const context = await chromium.launchPersistentContext('', {
    args: [
      '--headless=new',
      `--disable-extensions-except=${pathToExtension}`,
      `--load-extension=${pathToExtension}`,
      '--no-sandbox',
      '--disable-setuid-sandbox',
      '--disable-dev-shm-usage'
    ]
  });

  try {
    const background = await context.waitForEvent('backgroundpage', { timeout: 300000 });
    const extensionId = background.url().split('/')[2];
    console.log('Extension ID:', extensionId);
    
    testInfo.context = context;
    testInfo.extensionId = extensionId;
  } catch (error) {
    console.error('Error occurred while getting the extension ID:', error);
  } finally {
    await context.close();
  }
};

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.29 21:55:19