首页
/ 使用 @puppeteer/browsers 的 canDownload() 提前探测浏览器包是否可下载

使用 @puppeteer/browsers 的 canDownload() 提前探测浏览器包是否可下载

2026-09-07 17:25:31作者:邓越浪Henry

canDownload() 是 Puppeteer 官方浏览器管理库 @puppeteer/browsers 提供的公开 API,用于在真正执行安装之前判断某个浏览器(Chrome / ChromeDriver / Chrome for Testing / Firefox 等)的指定平台与 buildId 组合是否存在可下载的二进制归档。本文围绕其函数签名、参数语义与底层探测机制展开,结合仓库源码与测试用例,帮助你把它正确接入预检、断点续传、多镜像回退等下载流程。

canDownload() 的定位与使用场景

该函数属于 @puppeteer/browsers 的程序化(programmatic)API 家族。同族 API 还包括 install()getInstalledBrowsers()uninstall()getDownloadUrl(),它们统一从 packages/browsers/src/main.ts 导出。canDownload 本身是其中最轻量的一员:它不会下载任何字节,只负责回答"这个目标可不可下载"这一个布尔问题。

典型应用场景包括:

  • 在执行耗时的大体积浏览器下载前做可用性预检,避免失败后再报错;
  • 根据检测结果动态切换官方源与自定义镜像源;
  • 在 CI 中区分"目标版本暂未发布"与"网络故障"两类失败。

函数完整签名定义在 docs/browsers-api/browsers.candownload.md

export declare function canDownload(options: InstallOptions): Promise<boolean>;

它接受一个 InstallOptions 参数,返回 Promise<boolean>:当目标归档存在且可访问时解析为 true,否则为 false

传入参数:InstallOptions 逐项说明

canDownloadinstall 共用同一个 InstallOptions 配置对象(其 TypeScript 定义位于 packages/browsers/src/install.ts)。其中真正影响探测结果的字段如下。

字段 类型 必填 说明与默认值
browser Browser 枚举 目标浏览器。参考 Browser 枚举
buildId string 目标版本标识,应能唯一对应一份二进制,并作为缓存目录的组成部分
platform BrowserPlatform 枚举 目标操作系统与架构组合,如 LINUXMAC_ARMWIN64默认自动探测当前平台(调用 detectBrowserPlatform());若自动探测失败且未显式指定,函数会抛出异常
baseUrl string 下载源主机。默认是 https://storage.googleapis.com/chrome-for-testing-public(Chrome 系列)或 https://archive.mozilla.org/pub/firefox/nightly/latest-mozilla-central(Firefox)
providers BrowserProvider[] 自定义下载源提供者。多个可链式传入,按顺序尝试,官方默认源自动作为最后兜底
cacheDir string 否(探测时并不真正落盘) 浏览器安装根目录。canDownload 不创建目录,但保持与 install 一致的调用形态
logger Logger 调试日志输出(puppeteer:browsers:* 通道)

需要注意:installDepsexpectedHashunpackdownloadProgressCallbackbuildIdAlias 等字段更多服务于真正的安装流程,在 canDownload 中并不参与探测决策。

一个最小化的探测调用示例:

import {Browser, BrowserPlatform, canDownload} from '@puppeteer/browsers';

const available = await canDownload({
  browser: Browser.CHROME,
  buildId: '131.0.6778.85',
  platform: BrowserPlatform.LINUX,
  cacheDir: '/tmp/puppeteer-browsers',
});

console.log(available); // true | false

BrowserPlatform 的合法取值(枚举定义见 BrowserPlatform 枚举)按"OS 平台 × 架构"划分,例如 LINUXMACMAC_ARMWIN32WIN64,这决定了归档文件(如 chrome-linux64.zip)的选取。

底层探测原理:源码调用链

canDownload 的实现位于 packages/browsers/src/install.ts,整体逻辑可以概括为"拼接候选下载 URL → 逐个发送 HTTP HEAD 请求验证":

export async function canDownload(options: InstallOptions): Promise<boolean> {
  options.platform ??= detectBrowserPlatform();
  if (!options.platform) {
    throw new Error(
      `Cannot download a binary for the provided platform: ${os.platform()} (${os.arch()})`,
    );
  }

  // Always use plugin architecture (uses default provider if none specified)
  const providers = [
    ...(options.providers || []),
    new DefaultProvider(options.baseUrl),
  ];

  const downloadOptions = {
    browser: options.browser,
    platform: options.platform,
    buildId: options.buildId,
  };

  // Check if any provider can provide a valid, downloadable URL
  for (const provider of providers) {
    if (!(await provider.supports(downloadOptions))) {
      continue;
    }
    const url = await provider.getDownloadUrl(downloadOptions);
    if (url && (await headHttpRequest(url))) {
      return true;
    }
  }

  return false;
}

据此可以还原出它的关键行为,每一条都与具体代码一一对应:

  1. 平台自动补全:未显式提供 platform 时调用 detectBrowserPlatform();探测不到会直接抛错(错误信息形如 Cannot download a binary for the provided platform: linux (x64)),而不是静默返回 false
  2. Provider 插件化探测:即使不传 providers,也会构造一个 DefaultProviderDefaultProvidersupports() 恒返回 true,其 getDownloadUrl() 通过各浏览器的 downloadUrls 映射拼出归档地址,见 packages/browsers/src/DefaultProvider.ts。若传入了多个自定义 provider,则按数组顺序逐个尝试,任一 provider 命中即返回 true
  3. HEAD 请求验证存在性:核心校验由 headHttpRequest(url) 完成,见 packages/browsers/src/httpUtil.ts。它向 URL 发起 HTTP HEAD 请求,仅当响应状态码为 200 时才算可下载;同时会跟随 3xx 重定向,并在请求出错或抛异常时吞掉错误、返回 false——因此网络临时故障会被折算成"不可下载"。
  4. 短路返回:一旦某个 provider 的 URL 通过 HEAD 校验立即返回 true;所有 provider 都失败才返回 false。这意味着 canDownload 天然支持"公司内部镜像优先、官方源兜底"的多源回退语义。

与 install()、getDownloadUrl() 的分工协作

理解了调用链后,canDownload 在 API 家族中的位置就非常清晰:

  • install() 会真正下载、解压并安装浏览器归档(解压逻辑见 installWithProviders 对 provider 的遍历与回退);
  • getDownloadUrl(browser, platform, buildId, baseUrl) 只负责计算下载 URL,不发起任何网络请求,见 packages/browsers/src/install.ts
  • canDownload() 在两者之间:在 getDownloadUrl() 得到 URL 之后、install() 真正下载之前,用一次轻量 HEAD 请求确认该 URL 是否真实可达。

因此,一个稳妥的接入模式是先探测、后安装:

import {
  Browser,
  BrowserPlatform,
  canDownload,
  install,
} from '@puppeteer/browsers';

const target = {
  browser: Browser.CHROME,
  buildId: '131.0.6778.85',
  platform: BrowserPlatform.LINUX,
  cacheDir: './.browser-cache',
};

if (await canDownload(target)) {
  await install(target); // 确认可用后再执行真实安装
} else {
  console.warn('目标版本暂不可用,跳过安装');
}

测试用例如何验证探测行为

仓库为 canDownload 提供了覆盖"可下载 / 不可下载"两个方向的真实网络测试,可作为理解其语义的最佳佐证:

这些测试同时揭示了一个容易被忽略的细节:测试通过 baseUrl: getServerUrl() 指向本地测试服务器,说明 baseUrl 参数在探测中起决定性作用——它可以替换默认的官方下载源,这为自建内网镜像后复用 canDownload 做预检提供了依据。

注意事项与限制

综合源码与接口文档,使用时有以下几点需要留意:

  • 平台探测失败会抛异常:在无法识别平台的环境(如非标准 OS/架构组合)中,canDownload 不会返回 false,而是抛出 Cannot download a binary for the provided platform: ...。调用方应做好异常捕获。
  • 只验证"URL 可达",不验证"包体完整":HEAD 200 只代表资源存在;归档的 SHA-256 完整性校验依赖 install()expectedHash 参数,是两件不同的事。
  • 代理环境依赖可选依赖:库与 CLI 都遵循 HTTP_PROXYHTTPS_PROXYNO_PROXY 环境变量,但需要额外安装 proxy-agent 包才会走代理(见 docs/browsers-api/index.md),否则回落到 Node.js 默认 agent 直连。
  • 自定义 provider 不受官方保障providers 允许接入企业镜像等替代源,但文档明确提示 Custom providers 不在 Puppeteer 官方支持范围之内,二进制兼容性、功能集成与测试责任均由使用方自行承担。

综上,canDownload@puppeteer/browsers 中结构最简单、却非常适合放在"下载前"做预检的公共 API。把它的探测语义、返回时机(true / false / 抛错)与多 provider 链式回退机制纳入下载编排逻辑,可以有效提升浏览器自动管理的健壮性与可观测性。

登录后查看全文
热门项目推荐
相关项目推荐

项目优选

收起
kernelkernel
deepin linux kernel
C
33
18
ops-transformerops-transformer
本项目是CANN提供的transformer类大模型算子库,实现网络在NPU上加速计算。
C++
1.14 K
2.75 K
pytorchpytorch
作为 Ascend for PyTorch 社区的核心组件,TorchNPU 是昇腾专为 PyTorch 打造的深度学习适配插件,使 PyTorch 框架能够直接调用昇腾 NPU,为开发者提供昇腾 AI 处理器的超强算力。
Python
857
1.35 K
docsdocs
暂无描述
Markdown
897
5.8 K
kernelkernel
openEuler内核是openEuler操作系统的核心,既是系统性能与稳定性的基石,也是连接处理器、设备与服务的桥梁。
C
531
594
ops-nnops-nn
本项目是CANN提供的神经网络类计算算子库,实现网络在NPU上加速计算。
C++
916
1.83 K
jiuwenswarmjiuwenswarm
JiuwenSwarm 是一款基于openJiuwen开发的智能AI Agent,它能够将大语言模型的强大能力,通过你日常使用的各类通讯应用,直接延伸至你的指尖。
Python
3.58 K
1.01 K
ops-mathops-math
本项目是CANN提供的数学类基础计算算子库,实现网络在NPU上加速计算。
C++
1.36 K
1.46 K
cann-learning-hubcann-learning-hub
CANN 学习中心仓,支持在线互动运行、边学边练,提供教程、示例与优化方案,一站式助力昇腾开发者快速上手。
Jupyter Notebook
1.01 K
516
AscendNPU-IRAscendNPU-IR
AscendNPU-IR是基于MLIR(Multi-Level Intermediate Representation)构建的,面向昇腾亲和算子编译时使用的中间表示,提供昇腾完备表达能力,通过编译优化提升昇腾AI处理器计算效率,支持通过生态框架使能昇腾AI处理器与深度调优
C++
547
388