Documentation Index
Fetch the complete documentation index at: https://bun.zhcndoc.com/llms.txt
Use this file to discover all available pages before exploring further.
Bun.WebView 是内置在运行时中的无头浏览器。使用它来加载页面、在其中运行 JavaScript、模拟真实用户输入,并截取屏幕截图 — 不需要 Puppeteer、Playwright,也不需要单独下载浏览器。
此 API 为实验性质,可能会在后续版本中发生变化。
await using view = new Bun.WebView();
await view.navigate("https://example.com");
await view.click("a[href]"); // 等待链接变为可点击
const title = await view.evaluate("document.title");
await Bun.write("page.png", await view.screenshot());
在 macOS 上,Bun.WebView 使用系统的 WKWebView — 无需安装任何东西。在 Linux 和 Windows 上,它通过 Chrome DevTools Protocol 驱动已安装的 Chrome、Chromium、Edge 或 Brave。
每个视图都会在单独的渲染器进程中运行其页面。所有输入方法(click、type、press、scroll)都会分发原生浏览器事件,因此页面会看到 isTrusted: true — 与真实用户一致。
创建视图
const view = new Bun.WebView({
width: 1280, // 视口宽度(CSS 像素,1-16384,默认 800)
height: 720, // 视口高度(CSS 像素,1-16384,默认 600)
url: "https://bun.com", // 可选:立即开始导航
});
构造函数是同步的 — 它会立即返回,并在后台启动浏览器子进程。你第一次 await 的操作(navigate()、evaluate() 等)会等待浏览器准备就绪。
如果你传入 url,那么在构造函数返回之前视图就会开始导航。等价于在下一行调用 view.navigate(url)。
使用 using 的自动清理
Bun.WebView 实现了 Symbol.dispose 和 Symbol.asyncDispose,因此你可以使用 using 或 await using,当视图超出作用域时自动关闭:
{
await using view = new Bun.WebView();
await view.navigate("https://example.com");
// ...
} // 这里会自动调用 view.close()
持久化存储
默认情况下,每个视图使用短暂的内存存储 — cookies、localStorage、IndexedDB 和缓存都会在视图关闭时丢弃。要在多次运行之间持久化状态,请传入目录:
const view = new Bun.WebView({
dataStore: { directory: "./browser-profile" },
});
共享同一个 directory 的视图会共享 cookies 和存储。传入 dataStore: "ephemeral"(默认值)以显式回到内存存储。
使用 Chrome 后端时,dataStore.directory 会映射到 --user-data-dir,并作用于整个 Chrome 进程,
而不是每个视图。由于 Chrome 会在每个 Bun 进程中只启动一次,因此第一个视图的目录会赢,影响后续所有视图。
使用 WebKit 后端时,持久化存储需要 macOS 15.2+。在旧版本的 macOS 上,请使用 dataStore: "ephemeral"(默认值)。
Bun.WebView 支持两种渲染引擎。默认取决于你的平台:
| 后端 | 引擎 | 平台 | 需求 |
|---|
"webkit" | WKWebView | 仅 macOS | 无 — 使用系统 WebKit.framework |
"chrome" | Blink | macOS / Linux | 已安装 Chrome、Chromium、Edge 或 Brave(或 Playwright 的 chrome-headless-shell) |
在 macOS 上默认是 "webkit";其他平台上是 "chrome"。在非 macOS 平台请求 backend: "webkit" 会抛出异常。
// 在 macOS 上强制使用 Chrome
const view = new Bun.WebView({ backend: "chrome" });
WebKit 后端如何工作
Bun 会生成一个轻量的宿主子进程(bun 可执行文件本身,会以特殊模式重新执行),它在主线程上拥有 WKWebView。你的 Bun 进程通过 Unix socket 使用紧凑的二进制协议与它通信。宿主进程只会生成一次,并被程序中所有 "webkit" 视图共享。
Chrome 后端如何工作
Bun 要么 连接 到一个已经运行的 Chrome(通过 WebSocket),要么 生成 一个无头 Chrome 子进程,并通过管道与它通信(--remote-debugging-pipe)。无论哪种方式,通信都使用 Chrome DevTools Protocol。
Chrome 会在每个 Bun 进程中生成(或连接)一次。每个 new Bun.WebView({ backend: "chrome" }) 会在这一个 Chrome 实例中通过 Target.createTarget 创建一个新的标签页。
查找 Chrome 可执行文件
当 Bun 需要生成 Chrome 时,它会按以下顺序搜索:
- 你传入的
backend: { type: "chrome", path: "..." } 中的 path
BUN_CHROME_PATH 环境变量
$PATH(google-chrome-stable, google-chrome, chromium-browser, chromium, brave-browser, microsoft-edge, chrome)
- 标准安装位置(
/Applications/Google Chrome.app, ~/Applications/..., /usr/bin/..., /snap/bin/... 等)
- Playwright 缓存(
~/Library/Caches/ms-playwright 或 ~/.cache/ms-playwright)中的 chrome-headless-shell
如果找不到,会在构造函数中抛出。
连接到已在运行的 Chrome
默认情况下,在生成之前,Bun 会通过从标准 profile 目录读取 DevToolsActivePort 文件来检查某个 Chrome 家族浏览器是否已经在运行并启用了远程调试。如果找到,Bun 会通过 WebSocket 连接到该浏览器,而不是再生成一个 — 你的视图会作为标签页打开在现有浏览器中。
要在运行中的 Chrome 中启用远程调试,访问 chrome://inspect/#remote-debugging 并切换开关,或使用 --remote-debugging-port=9222 启动 Chrome。每次使用 chrome://inspect 开关连接到新的会话时,Chrome 都会在请求权限时提示。
要显式控制这一行为,请使用 backend 的对象形式:
// 总是生成一个新的无头 Chrome;永远不自动连接
new Bun.WebView({
backend: { type: "chrome", url: false },
});
// 连接到特定的 DevTools WebSocket URL
new Bun.WebView({
backend: {
type: "chrome",
url: "ws://127.0.0.1:9222/devtools/browser/abc123...",
},
});
如果自动探测发现过期的 DevToolsActivePort 文件(Chrome 崩溃或重启),WebSocket 连接将失败,并且 Bun 会透明地回退到生成自己的 Chrome。显式指定 url: "ws://..." 不会回退 — 连接失败会直接抛出异常。
传入 path 或 argv 会隐含进入生成模式并跳过自动探测。url: "ws://..." 不能与 path 或
argv 组合使用。
启动参数
生成时,Bun 会传入一组最小的参数:
--user-data-dir=<temp> --remote-debugging-pipe --headless --no-first-run
--no-default-browser-check --disable-gpu --disable-extensions
--disable-background-networking --disable-background-timer-throttling
--disable-backgrounding-occluded-windows --disable-renderer-backgrounding
--disable-ipc-flooding-protection --no-startup-window
用 argv 把你自己的参数追加进去 — Chrome 处理重复开关时采用“最后生效”,因此你可以覆盖任意默认值:
new Bun.WebView({
backend: {
type: "chrome",
argv: ["--headless=new", "--lang=ja-JP", "--window-size=1920,1080"],
},
});
子进程输出
默认情况下会静默浏览器子进程的 stdout/stderr。特别是 Chrome 的 stderr 很“吵”(字体配置警告、GCM 注册、更新检查)。如果你想看到它(在 Chrome 静默崩溃时尤其有用),请这样转发:
new Bun.WebView({
backend: { type: "chrome", stderr: "inherit", stdout: "inherit" },
});
"webkit" 后端也接受相同的 stdout/stderr 选项。
await view.navigate("https://example.com");
await view.navigate("data:text/html,<h1>hello</h1>");
await view.navigate("file:///path/to/index.html");
当主框架的 load 事件触发时,navigate() 才会解析完成。解析完成后,view.url 和 view.title 会反映新页面,且 view.loading 为 false。
如果导航失败(DNS 失败、连接被拒绝、URL 无效),该 promise 会以描述失败原因的 Error 形式拒绝。
每个视图在任一时刻只能进行一个正在进行的导航。若在另一个 navigate() 仍待处理时再次调用 navigate(),会同步抛出 ERR_INVALID_STATE。
历史记录
await view.goBack(); // 类似浏览器的返回按钮
await view.goForward(); // 类似浏览器的前进按钮
await view.reload(); // 重新加载当前页面
在历史记录的起点(或终点)调用 goBack()(或 goForward())会直接解析为 undefined,不进行导航 — 不会拒绝。
导航回调
设置 onNavigated 和 onNavigationFailed 来观察每一次导航,包括页面自身触发的导航(点击链接、location.href = ...、重定向)以及由 reload()/goBack()/goForward() 触发的导航:
view.onNavigated = (url, title) => {
console.log("Loaded", url);
};
view.onNavigationFailed = error => {
console.error("Navigation failed:", error.message);
};
这些回调会在对应的 navigate() promise 完成(settle)之前触发,因此当你 await view.navigate(...) 返回时,你的回调已经运行过了。设置为 null 可移除。
计算 JavaScript
在页面的主框架中运行一个表达式,并把结果作为原生 JavaScript 值返回:
const title = await view.evaluate("document.title");
const items = await view.evaluate("[...document.querySelectorAll('li')].map(li => li.textContent)");
const user = await view.evaluate("({ name: 'bun', ok: true })");
脚本会被包装为 await (<your script>),因此:
- 它必须是一个表达式,而不是语句序列。要包含多条语句请用 IIFE 包裹:
evaluate("(() => { let x = foo(); return x + 1 })()")。
- 如果它计算为一个
Promise,会等待该 promise 并返回其解析值。
结果会在页面侧通过 JSON.stringify,在 Bun 侧通过 JSON.parse 来往返传递。数组和普通对象会以真实结构返回;undefined、函数和 symbol 会解析为 undefined;循环引用会导致拒绝。
await view.evaluate("42"); // 42
await view.evaluate("[1, 2, 3]"); // [1, 2, 3]
await view.evaluate("undefined"); // undefined
await view.evaluate("() => 1"); // undefined(函数不会序列化)
await view.evaluate("fetch('/api').then(r => r.json())"); // 已等待
如果脚本抛出异常(或返回被拒绝的 promise),evaluate() 会拒绝,并把消息作为页面侧异常信息的一部分返回一个 Error。
每个视图在任一时刻只能进行一个正在进行的 evaluate();第二个并发调用会同步抛出 ERR_INVALID_STATE。
把当前视口捕获成图片:
const png = await view.screenshot();
await Bun.write("page.png", png);
图片格式
await view.screenshot({ format: "png" }); // 无损(默认)
await view.screenshot({ format: "jpeg", quality: 90 }); // 有损,quality 0-100(默认 80)
await view.screenshot({ format: "webp", quality: 75 }); // 仅 Chrome 后端
PNG 会忽略 quality。"webp" 只在 backend: "chrome" 时可用 — WebKit 后端会抛出异常。
返回类型
encoding 选项控制图片字节如何返回给你:
encoding | 返回内容 | 说明 |
|---|
"blob" (默认) | Blob | MIME 类型自动设置。WebKit 上基于 mmap 的零拷贝。可与 Bun.write()、new Response() 一起使用 |
"buffer" | Buffer | Node Buffer。WebKit 上基于 mmap 的零拷贝 |
"base64" | string | Base64 编码。Chrome 上无需解码(CDP 原生返回 base64) |
"shmem" | { name: string, size: number } | POSIX 共享内存段名称。调用方负责 shm_unlink。Windows 不支持 |
const buf = await view.screenshot({ encoding: "buffer" });
console.log(buf[0] === 0x89); // PNG 魔术字节
const b64 = await view.screenshot({ encoding: "base64" });
console.log(`<img src="data:image/png;base64,${b64}">`);
终端图形的共享内存
encoding: "shmem" 专为 Kitty 的 终端图形协议 t=s 传输模式设计 — Bun 会把图片写入一个 POSIX 共享内存段并返回其名称;终端直接读取,并在完成后取消链接(unlinks)。无需通过管道复制。
const { name, size } = await view.screenshot({ encoding: "shmem" });
process.stdout.write(`\x1b_Gf=100,t=s,a=T,S=${size};${btoa(name)}\x1b\\`);
// Kitty 从共享内存读取 PNG 并取消链接该段
在 WebKit 上,shm 名称看起来像 /bun-webview-<pid>-<seq>;在 Chrome 上是 /bun-chrome-<pid>-<seq>。如果你请求 "shmem",但没有把名称交给某个会执行 shm_unlink 的逻辑,那么共享内存段会在你的进程退出前一直泄漏。
输入模拟
所有输入方法都会分发原生浏览器事件。页面会收到 pointerdown/mousedown/keydown/wheel 事件,且带有 isTrusted: true;CSS :active 与 :hover 状态会生效,并且默认行为(表单提交、链接导航、文本选择)会像真实用户操作那样准确触发。
在视口坐标处点击:
await view.click(150, 200);
await view.click(150, 200, { button: "right" });
await view.click(150, 200, { clickCount: 2 }); // 双击
await view.click(150, 200, { modifiers: ["Shift", "Meta"] });
该 promise 会在页面处理完整的 mousedown → mouseup → click 序列之后才解析完成,包括任何 JavaScript 处理器。无需轮询 — 随后的 evaluate() 会看到结果。
通过选择器点击
传入 CSS 选择器而不是坐标,Bun 会等待该元素变为可操作(actionable),然后点击它的中心:
await view.click("#submit");
await view.click("button.primary", { timeout: 5000 });
当元素满足以下条件时,它才是可操作的:
- 存在于 DOM 中
- 拥有非零的边界框
- 位于视口内
- 已保持稳定(在连续两帧动画中边界框未改变)
- 在其中心点处是最上层元素(没有被覆盖物遮挡)
该检查会在页面侧以 requestAnimationFrame 的频率运行。如果该元素在 timeout 毫秒内始终未变为可操作(默认 30000),promise 会以类似 timeout waiting for '#submit' to be actionable 的错误拒绝。
选择器作为数据传递,而不是插值进脚本,因此包含引号或 JavaScript 语法的选择器是安全的。
输入文本
把文本插入到当前聚焦的元素中:
type() 使用浏览器的 InsertText 编辑命令(与粘贴使用同一路径),而不是逐字符的按键模拟。它会触发带 isTrusted: true 的 beforeinput/input 事件,但不会触发 keydown/keyup 事件。不会进行 IME 处理,也不会进行智能引号替换 — 文本会被按原样精确写入。
按下按键
await view.press("Enter");
await view.press("Escape");
await view.press("ArrowDown");
await view.press("a", { modifiers: ["Meta"] }); // Cmd+A / Ctrl+A
命名的虚拟按键:Enter、Tab、Space、Backspace、Delete、Escape、ArrowLeft、ArrowRight、ArrowUp、ArrowDown、Home、End、PageUp、PageDown。
任意单字符(例如 "a")结合 modifiers 会发送一个按键组合键(chord)。
在 WebKit 后端,大多数命名按键(不带修饰键)会映射到编辑命令(DeleteBackward、MoveLeft、InsertNewline 等),并在页面应用之后解析完成。Escape、Space,以及任何带修饰键的按键会回退到原始的 keydown/keyup 事件 — 这些事件会触发一个页面可观察到的 keydown,但没有“完成屏障”,所以如果你需要观察其效果,请在后面跟一个 evaluate()。
修饰键名称:"Shift"、"Control"(或 "Ctrl")、"Alt"(或 "Option")、"Meta"(或 "Cmd" / "Command")。
按像素增量滚动 — 在视口中心触发一个原生 wheel 事件:
await view.scroll(0, 500); // 向下滚动 500px
await view.scroll(-100, 0); // 向左滚动 100px
正的 dy 会向下滚动(内容向上移动),与 window.scrollBy 一致。如果视口中心下方有可滚动元素,它会接收到 wheel 事件,而不是整个文档。
通过选择器把元素滚入视野:
await view.scrollTo("#footer"); // 居中显示(默认)
await view.scrollTo("#hero", { block: "start" }); // 让元素顶部对齐视口顶部
await view.scrollTo(".card", { block: "nearest" }); // 最小滚动
scrollTo() 会以 requestAnimationFrame 的频率等待元素存在,然后调用 element.scrollIntoView({ block, behavior: "instant" })。它会滚动所有可滚动祖先,而不仅仅是文档。默认 timeout 为 30000 ms。
调整大小
await view.resize(1920, 1080);
宽度和高度分别必须在 1 到 16384 之间。
控制台捕获
通过在构造函数中传入 console 选项,把页面侧的 console.* 调用转发到你的 Bun 进程。
镜像到 Bun 的控制台
传入 globalThis.console(实际对象,按引用)后,页面侧 console.log("hi") 会以 Bun 的格式化器把 hi 输出到你的 stdout;console.error 输出到 stderr。此路径会直接通过 Bun 的控制台实现分发,不会为每次调用引入额外的 JavaScript 开销。
const view = new Bun.WebView({
console: globalThis.console,
});
自定义处理器
传入一个函数来接收每次调用:
const view = new Bun.WebView({
console: (type, ...args) => {
// type 是 "log" | "warn" | "error" | "info" | "debug" | ...
if (type === "error") reportError(args);
},
});
原始参数(字符串、数字、布尔值、null、undefined)会解包为它们的原始值。对象参数会以序列化描述符的形式到达:
- Chrome 后端:原始的 CDP
RemoteObject — 一个包含 type、className、description,以及(在可用时)preview.properties 数组的对象。
- WebKit 后端:对象经过
JSON.stringify 往返后的结果。函数、循环引用以及其他不可序列化值会回退为 String(...) 的强制转换。
如果你不传 console,页面侧的控制台输出会被丢弃。
顺序保证:在你传给 evaluate() 的脚本内部执行的 console.log(...) 会在该 evaluate() promise 解析完成之前交付给你的处理器。两者会通过同一条 IPC 连接传输。
原始 Chrome DevTools Protocol
当使用 backend: "chrome" 时,如果高层 API 没有覆盖你想要的能力,你可以直接切换到原始的 CDP 命令。
发送命令
const view = new Bun.WebView({ backend: "chrome" });
await view.navigate("https://example.com"); // 必需:设置 CDP 会话
await view.cdp("Emulation.setUserAgentOverride", {
userAgent: "MyBot/1.0",
});
const { root } = await view.cdp("DOM.getDocument");
const { nodeId } = await view.cdp("DOM.querySelector", {
nodeId: root.nodeId,
selector: "input[name=q]",
});
await view.cdp("DOM.focus", { nodeId });
cdp(method, params?) 会返回 CDP 响应中的 result 对象。如果 Chrome 返回错误(未知方法、参数错误),该 promise 会以 error.message 拒绝。
命令会被限定在此视图的会话范围内(目标是此标签页)。在调用 cdp() 之前至少要 await navigate(...) 一次 — 第一次导航会建立会话。若在那之前调用 cdp() 会抛出 ERR_INVALID_STATE。
params 必须是可 JSON 序列化的对象;对于不带参数的命令可省略。每个视图同一时刻最多只能有一个 cdp() 调用正在进行。
订阅事件
Bun.WebView 继承自 EventTarget。在 Chrome 后端下,CDP 事件会作为 DOM 事件分发:type 为 CDP 方法名,data 为解析后的 params 对象:
await view.navigate("about:blank");
await view.cdp("Network.enable"); // 仅 Chrome:只有启用了域才会发出事件
view.addEventListener("Network.responseReceived", event => {
console.log(event.data.response.status, event.data.response.url);
});
await view.navigate("https://example.com");
如果没有为某个事件注册监听器,它会在 JSON params 解析之前就被丢弃,因此如果你只监听一两种事件类型,开启“啰嗦”的域(例如 Network)也不会太贵。
在 WebKit 后端上,cdp() 会抛出 ERR_METHOD_NOT_IMPLEMENTED — 没有 DevTools Protocol 的桥接。EventTarget 接口仍然可用于你自己对 dispatchEvent() 的调用。
生命周期
关闭视图
关闭是同步且可重复调用(幂等)的。它会销毁页面的渲染器进程,并用 Error("WebView closed") 拒绝视图上所有待处理的 promise,同时让之后对该视图的所有方法调用都会抛出 ERR_INVALID_STATE。
view[Symbol.dispose] 和 view[Symbol.asyncDispose] 都指向 close(),所以 using / await using 可以正常工作。
杀死所有浏览器
强制终止(SIGKILL)所有浏览器子进程(包括 Chrome 子进程和 WebKit 宿主子进程)。每个视图上的待处理 promise 会在下一次事件循环 tick 时拒绝。之后的 new Bun.WebView() 调用会在需要时重新生成。
Bun 会在进程退出时自动调用它,因此浏览器子进程不会在你的脚本之外存活。
事件循环行为
浏览器子进程不会自行保持 Bun 的事件循环存活。只要存在打开的 WebView 且它还有未完成的操作(例如未 settle 的 navigate()、evaluate() 等),进程就会保持运行。你关闭最后一个视图 — 或最后一个待处理操作完成(settle)之后 — Bun 会自然退出。
子进程死亡
如果浏览器子进程意外死亡(崩溃、OOM-kill、SIGKILL),则所有视图上的待处理 promise 都会以描述死亡原因的错误拒绝(例如 "Chrome killed by signal 9"、"WebView host process died" 等),并且对这些视图的后续操作会抛出异常。
并发模型
每个视图都有少量用于并发的独立“操作槽位”。同一种操作在任一时刻最多只有一个在飞行(in flight):
- 一个
navigate()(在 Chrome 后端与 reload()/goBack()/goForward() 共享)
- 一个
evaluate()
- 一个
screenshot()
- 一个
cdp()(仅 Chrome)
- 一个“简单”操作 —
click()、type()、press()、scroll()、scrollTo()、resize()(以及 WebKit 后端的 reload()/goBack()/goForward())共享此槽位
当某个槽位已被占用时,在启动第二个该类型操作会同步抛出 ERR_INVALID_STATE — 不会排队。在实际使用中,直接对每次调用 await 即可。
不同视图之间的操作完全独立,并会并行运行 — 每个视图都有自己的渲染器进程。
new Bun.WebView(options?)
| 选项 | 类型 | 默认值 | 描述 |
|---|
width | number | 800 | 视口宽度(CSS 像素)。范围 1-16384。 |
height | number | 600 | 视口高度(CSS 像素)。范围 1-16384。 |
url | string | — | 立即开始导航到该 URL。 |
headless | boolean | true | 仅实现 true;false 会抛出异常。 |
backend | "webkit" | "chrome" | object | macOS 为 "webkit",其他为 "chrome" | 渲染引擎。 |
console | typeof console | (type, ...args) => void | — | 捕获页面侧的 console.* 调用。见 控制台捕获。 |
dataStore | "ephemeral" | { directory: string } | "ephemeral" | cookies / localStorage / IndexedDB 的存储。见 持久化存储。 |
backend 对象形式
| 选项 | 类型 | 描述 |
|---|
type | "chrome" | "webkit" | 必填。 使用哪个引擎。 |
path | string | (chrome only)Chrome/Chromium 可执行文件的路径。强制进入生成模式。 |
argv | string[] | (chrome only)额外的启动参数,会在默认参数之后追加。强制进入生成模式。 |
url | string | false | (chrome only)现有 Chrome 的 DevTools 端点 ws:// URL;或传 false 跳过自动探测并始终生成。见 上文。 |
stdout | "inherit" | "ignore" | 把子进程的 stdout 转发到 Bun。默认 "ignore"。 |
stderr | "inherit" | "ignore" | 把子进程的 stderr 转发到 Bun。默认 "ignore"。 |
实例属性
| 属性 | 类型 | 描述 |
|---|
url | string (readonly) | 当前 URL。导航完成后更新。首次导航前为空字符串。 |
title | string (readonly) | 页面 <title>。导航完成后更新。 |
loading | boolean (readonly) | 当正在进行导航时为 true。 |
onNavigated | ((url: string, title: string) => void) | null | 每次成功导航后触发:在 navigate() promise 解析前触发。 |
onNavigationFailed | ((error: Error) => void) | null | 每次失败导航后触发:在 navigate() promise 拒绝前触发。 |
实例方法
| 方法 | 返回值 | 描述 |
|---|
navigate(url) | Promise<void> | 加载一个 URL。会在主框架的 load 事件触发时解析完成。 |
evaluate(script) | Promise<unknown> | 在页面中运行一个 JS 表达式,并返回其 JSON 序列化后的结果。 |
screenshot(options?) | Promise<Blob | Buffer | string | {name, size}> | 截取视口。见 截图。 |
click(x, y, options?) | Promise<void> | 在视口坐标处进行原生点击。 |
click(selector, options?) | Promise<void> | 等待元素变为可操作,然后点击其中心。 |
type(text) | Promise<void> | 通过 InsertText 编辑命令向聚焦元素插入文本。 |
press(key, options?) | Promise<void> | 按下一个命名虚拟按键或单字符组合键。 |
scroll(dx, dy) | Promise<void> | 在视口中心触发一个原生 wheel 事件。dx/dy 必须是有限值。 |
scrollTo(selector, options?) | Promise<void> | 等待元素存在,然后调用 scrollIntoView。 |
resize(width, height) | Promise<void> | 修改视口尺寸。每个维度 1-16384。 |
goBack() | Promise<void> | 在会话历史中向后导航。在起点为无操作(no-op)。 |
goForward() | Promise<void> | 在会话历史中向前导航。在终点为无操作(no-op)。 |
reload() | Promise<void> | 重新加载当前页面。 |
cdp(method, params?) | Promise<unknown> | (仅 Chrome)向该标签页发送一个作用域限定的原始 CDP 命令。见 原始 CDP。 |
addEventListener(type, fn) | void | 从 EventTarget 继承而来。对于 Chrome,type 可能是一个 CDP 事件名;event.data 是解析后的 params。 |
close() | void | 销毁页面。拒绝所有待处理 promise。幂等。 |
click() 选项
| 选项 | 类型 | 默认值 | 描述 |
|---|
button | "left" | "right" | "middle" | "left" | 鼠标按键。 |
modifiers | ("Shift" | "Control" | "Alt" | "Meta")[] | [] | 点击时按住的修饰键。 |
clickCount | 1 | 2 | 3 | 1 | 双击/三击的点击次数。 |
timeout | number | 30000 | (仅选择器重载)等待可操作性的最长毫秒数。 |
press() 选项
| 选项 | 类型 | 默认值 | 描述 |
|---|
modifiers | ("Shift" | "Control" | "Alt" | "Meta")[] | [] | 按下按键时按住的修饰键。 |
| 选项 | 类型 | 默认值 | 描述 |
|---|
block | "start" | "center" | "end" | "nearest" | "center" | 滚动后的垂直对齐方式。 |
timeout | number | 30000 | 等待元素存在的最长毫秒数。 |
screenshot() 选项
| 选项 | 类型 | 默认值 | 描述 |
|---|
format | "png" | "jpeg" | "webp" | "png" | 图片格式。"webp" 需要 Chrome 后端。 |
quality | number | 80 | 0-100。仅 JPEG/WebP;PNG 会忽略。 |
encoding | "blob" | "buffer" | "base64" | "shmem" | "blob" | 返回类型编码。Windows 不支持 "shmem"。 |
静态方法
| 方法 | 描述 |
|---|
WebView.closeAll() | SIGKILL 每个浏览器子进程。下一 tick 上拒绝所有待处理 promise。退出时自动调用。 |