2026西湖龙井茶官网DTC发售:茶农直供,政府溯源防伪到农户家
大多数“免费在线工具”都遵循相同的模式:将文件上传到服务器,使用后端脚本进行处理,然后返回结果。这种方法虽然可行,但会带来隐私问题。您处理的每个文件都会经过他人的基础设施。
我想证明存在一种更好的方法。在 77 天的时间里,我构建了 ToolKnit —— 一套包含 72 种免费在线工具的套件,其中零文件离开用户的设备。没有后端处理。没有服务器上传。一切都在浏览器中运行。
以下是我的实现方法、所学到的经验以及失败之处。
核心架构
ToolKnit 是一个静态网站。没有 Node.js 服务器,没有 Django 应用,也没有无服务器函数。只有 HTML、Tailwind CSS 和原生 JavaScript,运行在每月 5 美元的虚拟专用服务器上的 Nginx 之后。唯一的服务器端代码是一个单独的 PHP 脚本(track.php),用于记录匿名页面加载次数 —— 不进行文件处理,不收集用户数据。
每个工具都是一个独立的 HTML 页面,拥有自己的 JavaScript 文件。当您访问 compress-pdf.html 时,整个 PDF 压缩流程都在您的浏览器中使用以下技术运行:
- PDF-lib.js 用于 PDF 操作(压缩、合并、拆分)
- Canvas API 用于图像处理(裁剪、调整大小、转换)
- FFmpeg.wasm 用于视频和音频转换(从 C 语言编译为 WebAssembly)
- Web Audio API 用于音频分析(每分钟节拍数检测、波形可视化)
- 文件系统访问 API 用于读取和写入本地文件
用户选择文件,浏览器在本地处理该文件,结果直接从内存下载。文件永远不会接触服务器。
WebAssembly:关键赋能者
最大的技术赋能者是 WebAssembly。如果没有它,视频转音频、音频修剪和视频转 GIF 等工具在浏览器中将无法实现。我使用 FFmpeg.wasm(FFmpeg 的 WebAssembly 移植版本)来处理所有媒体转换任务。
代价是体积。FFmpeg.wasm 使初始加载增加了大约 25MB。为了缓解这个问题,我采用懒加载方式 —— 仅在用户实际选择媒体文件时才加载它。核心工具页面以轻量级用户界面瞬间加载,而 WebAssembly 模块则在用户选择文件时在后台下载。
多线程 FFmpeg.wasm 需要 SharedArrayBuffer,这意味着每个媒体工具页面都需要跨源隔离标头(COOP 和 COEP)。我通过一个服务工作线程(coi-serviceworker.js)来处理这个问题,它会动态注入所需的标头,因此我不需要为每个工具单独配置 Nginx。
服务工作线程策略
ToolKnit 是一个具有激进缓存策略的渐进式 Web 应用。服务工作线程(service-worker.js)在安装时会预缓存所有工具页面、JavaScript 文件和博客文章。这意味着:
- 离线访问 —— 首次访问后,所有工具无需互联网连接即可工作
- 即时加载 —— 后续访问从缓存加载,并在后台更新
-
版本管理 —— 每次部署都会增加缓存版本(当前为
toolknit-v67)
挑战在于缓存失效。每次我添加工具或修复错误时,都需要提升缓存版本并更新 PRECACHE_URLS 数组。早期,我在部署后忘记提升版本,导致用户被困在旧版本中数天。现在,这已成为我部署检查清单的一部分 —— 毫无例外。
改变一切的部署灾难
免责声明:本文内容来自互联网,该文观点不代表本站观点。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,请到页面底部单击反馈,一经查实,本站将立刻删除。
免责声明:本文内容来自互联网,该文观点不代表本站观点。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,请到页面底部单击反馈,一经查实,本站将立刻删除。