跳转到内容

处理文件

发布于

一句话概括: 在 Web App Manifest 中声明 file_handlers,会将已安装的 PWA 注册为 操作系统对特定文件类型的处理程序,这样双击或使用“打开方式”打开匹配的文件时会直接以该 文件启动你的应用,而无需你自己搭建一套单独的导入流程。

根据 Chrome for Developers 的说明,每个文件处理程序都需要一个位于应用作用域内的 action URL、一个将 MIME 类型映射到文件扩展名的 accept 对象,以及一个可选的 icons 数组,使操作系统能够展示特定文件类型的图标而不只是应用图标:

{
"file_handlers": [
{
"action": "/open-csv",
"accept": { "text/csv": [".csv"] },
"icons": [
{ "src": "/icons/csv-icon.png", "sizes": "256x256", "type": "image/png" }
],
"launch_type": "single-client"
}
]
}

launch_type 决定同时打开多个匹配文件时是复用同一个应用窗口("single-client", 默认值),还是使用 "multiple-clients" 为每个文件各启动一次应用,每次启动的 LaunchParams.files 数组仅包含该文件。

2. 用 launchQueue 接收被启动的文件

Section titled “2. 用 launchQueue 接收被启动的文件”

根据 MDN 的说明,一旦操作系统以匹配的文件启动应用,应用会通过 window.launchQueue.setConsumer() 接收该文件:

window.launchQueue.setConsumer(async (launchParams) => {
if (!launchParams.files.length) {
return;
}
const [fileHandle] = launchParams.files;
const file = await fileHandle.getFile();
const text = await file.text();
renderCsv(text);
});
  • 图例
  • 支持
  • 部分支持
  • 需开启标志
  • 不支持
  • 未知
浏览器 / 平台支持版本置信度来源备注
Chrome (Desktop)支持102高来源—
Chrome (Android)不支持—高来源1
Edge (Desktop)支持102高来源2
Firefox (Desktop)不支持—高来源3
Firefox (Android)不支持—高来源45
Safari (macOS)不支持—高来源6
Safari (iOS)不支持—高来源78
Samsung Internet不支持—高来源910
WebView (Android)不支持—高来源1112
  1. browser-compat-data 未记录 Chrome Android 的支持。
  2. 由 browser-compat-data 镜像自 Chrome 的数据推导。
  3. browser-compat-data 未记录 Firefox 的支持。
  4. browser-compat-data 未记录 Firefox for Android 的支持。
  5. 由 browser-compat-data 镜像自 Firefox 的数据推导。
  6. browser-compat-data 未记录 Safari 的支持。
  7. browser-compat-data 未记录 iOS 版 Safari 的支持。
  8. 由 browser-compat-data 镜像自 Safari 的数据推导。
  9. browser-compat-data 未记录 Samsung Internet 的支持。
  10. 由 browser-compat-data 镜像自 Chrome Android 的数据推导。
  11. browser-compat-data 未记录 WebView Android 的支持。
  12. 由 browser-compat-data 镜像自 Chrome Android 的数据推导。

源数据: /compatibility/manifest-file-handlers.json · 全球使用占比: 37 % (StatCounter 2026-05)

来源: 规范 · MDN · 最近核验 2026-10-03 · 置信度: 高 (由来源计算)

根据 Chrome for Developers 的说明,文件处理在 Chromium 的实现中“仅限于桌面操作系统”—— 不要指望它能在 Android 上把文件与应用关联起来。

根据 Chrome for Developers 的说明,请同时使用 "launchQueue" in window 与 "files" in LaunchParams.prototype 两项特性检测,因为仅有 launchQueue 并不能确认 consumer 所依赖的 files 参数形态。当任意一项检测失败时,为用户提供一个不依赖操作 系统注册的应用内打开方式:

function supportsFileHandling() {
return 'launchQueue' in window && 'files' in LaunchParams.prototype;
}
if (supportsFileHandling()) {
window.launchQueue.setConsumer(async (launchParams) => {
if (!launchParams.files.length) return;
const file = await launchParams.files[0].getFile();
renderCsv(await file.text());
});
} else {
// 此处不支持 File Handling——改用界面中手动的
// <input type="file" accept=".csv"> 选择器。
document.getElementById('open-file-input').hidden = false;
}
  • 根据 Chrome for Developers 的说明,file_handlers 注册在 Chromium 中仅限桌面端—— 务必始终提供一个应用内文件选择器,作为 Android 端或回退路径。
  • 请同时使用 "launchQueue" in window 与 "files" in LaunchParams.prototype 两项检测(根据 Chrome for Developers 的说明)——仅检测 launchQueue 无法确认 setConsumer() 回调所依赖的 files 参数形态。
  • 根据 Chrome for Developers 的说明,launchQueue 会将启动事件排队,直到有 consumer 被注册,且无论何时注册,每次启动都会被处理且仅处理一次——但 consumer 函数本身仍 必须先运行才能读到被启动的文件,因此不要把它的注册挂在其他异步启动逻辑之后。
  • Firefox 与 Safari 均未实现 file_handlers——不要把操作系统级别的文件关联当作进入 该功能的唯一方式。