
rclone 编译为 WASM在浏览器中以 JavaScript 库方式调用 rclone RC 接口【免费下载链接】rclonersync for cloud storage - Google Drive, S3, Dropbox, Backblaze B2, One Drive, Swift, Hubic, Wasabi, Google Cloud Storage, Azure Blob, Azure Files, Yandex Files项目地址: https://gitcode.com/GitHub_Trending/rc/rclonerclone 的 fs/rc/js/ 目录提供了一套完整的WebAssembly 化示例通过GOOSjs GOARCHwasm将 rclone 的 rcremote control核心编译为rclone.wasm再借助 JavaScript 加载器在浏览器中直接调用 rclone 的 rc 方法如core/version、operations/mkdir从而把 rclone 变成可在 Web 页面内运行的存储操作库。读完本文你将理解这套编译、加载、调用的完整链路从 Go 侧通过syscall/js导出rc全局函数到 JS 侧用 Promise 等待 WASM 就绪并发起调用再到错误状态码如何从 Go 错误类型映射为 HTTP 语义状态。目录结构与各文件职责fs/rc/js/README.md 对该目录的文件清单有明确说明实际目录内容与其一致文件作用index.html测试网页仅加载loader.js并提示check the consoleloader.js加载 WASM 模块的 JavaScript文末附带用法示例main.go导出 rclone rc 的 Go 主代码构建标签jsMakefile测试用 makefile定义build与serve两个目标serve.go测试用静态文件服务器在localhost:3000上提供页面wasm_exec.js来自 Go 源码的官方运行时接口代码不要修改index.html的实现非常精简——页面本身几乎没有任何 DOM 内容一切交互都发生在控制台!doctype html html head meta nameviewport contentwidthdevice-width, initial-scale1.0 titleRclone/title /head body script srcloader.js/script pWelcome to rclone - check the console/p /body /html编译两步 Makefile 与等价的手动命令fs/rc/js/README.md 给出的编译方式有两种二者等价make # 或者手动执行 GOARCHwasm GOOSjs go build -o rclone.wasmMakefile 中定义的两个目标完整内容如下build: GOARCHwasm GOOSjs go build -o rclone.wasm serve: build go run serve.go其中build目标产出rclone.wasm二进制serve目标先依赖build再运行 serve.go。serve.go带//go:build none标签因此不会被go build误编入 WASM 目标其逻辑是注册 MIME 类型.wasm - application/wasm、.js - application/javascript——这一步对WebAssembly.instantiateStreaming正确识别响应类型至关重要用http.FileServer把当前目录挂到根路径监听:3000控制台会打印Serving on http://localhost:3000/。加载链路loader.js 如何启动 WASMloader.js 是整个浏览器端的入口完整流程分三步声明就绪信号在文件头部创建一个 PromiseGo 侧编译产物启动成功后会调用rcValidResolve将其 resolvevar rcValidResolve var rcValid new Promise(resolve { rcValidResolve resolve });注入 wasm_exec.js 并实例化动态插入script srcwasm_exec.js在其加载完成后对缺失WebAssembly.instantiateStreaming的旧浏览器做 polyfill先取 arrayBuffer 再WebAssembly.instantiate然后new Go()并以fetch(rclone.wasm)流式实例化script.onload function () { if (!WebAssembly.instantiateStreaming) { // polyfill WebAssembly.instantiateStreaming async (resp, importObject) { const source await (await resp).arrayBuffer(); return await WebAssembly.instantiate(source, importObject); }; } const go new Go(); WebAssembly.instantiateStreaming(fetch(rclone.wasm), go.importObject).then((result) { go.run(result.instance); }); };等待就绪后调用 rc在rcValid.then(...)回调中演示四个调用示例rcValid.then(() { // The rc call takes two parameters, method and input object and // returns an output object. // If the output object has an error and a status then it is an // error (it would be nice to signal this out of band). console.log(core/version, rc(core/version, null)) console.log(rc/noop, rc(rc/noop, {string:one,number:2})) console.log(operations/mkdir, rc(operations/mkdir, {fs::memory:,remote:bucket})) console.log(operations/list, rc(operations/list, {fs::memory:,remote:bucket})) })按 fs/rc/js/README.md 的Running章节运行make serve后访问 http://localhost:3000/打开浏览器 JavaScript 控制台即可看到这四行 rc 调用的输出loader.js末尾就是官方推荐的用法参照。Go 侧实现main.go 导出的 rc 全局函数main.go 带//go:build js构建标签是 WASM 侧的胶水层。依赖引入决定了能力边界main.go 的 import 块决定了这个 WASM 库装了什么import ( ... github.com/rclone/rclone/fs github.com/rclone/rclone/fs/rc // Core functionality we need _ github.com/rclone/rclone/fs/operations _ github.com/rclone/rclone/fs/sync // _ github.com/rclone/rclone/backend/all // import all backends // Backends _ github.com/rclone/rclone/backend/memory )fs/operations、fs/sync的空导入触发了其中rc.Add的注册因此 WASM 内可用operations/*mkdir、list 等与 sync 相关的 rc 方法注释掉的backend/all表明默认只引入backend/memory这一个内存后端示例中即使用:memory:作为fs若需支持其他后端可在此处按需替换空导入再重新执行GOARCHwasm GOOSjs go build -o rclone.wasm。从源码结构看由于云存储后端普遍依赖网络 OAuth 流程浏览器内可直接使用的仍是 memory 这类无需外部凭证的后端。main() 的初始化序列main()依次完成四件事检查js.Global()、document、JSON是否存在缺失则log.Fatalf说明未运行在浏览器中导出核心 APIjs.Global().Set(rc, js.FuncOf(rcCallback))—— 这正是 loader.js 中可直接调用的全局函数rc(method, input)调用宿主页面预定义的rcValidResolve通知 loader.js 的 Promise模块已就绪与 loader.js 第 3–5 行的信号机制一一对应select {}永久阻塞让 Go 运行时常驻以响应后续的 JS 调用。rcCallback一次调用的完整生命周期rcCallback是浏览器与 rclone 之间的唯一入口签名固定为rc(method, in)处理链如下参数校验必须恰好 2 个参数args[0]为方法名字符串args[1]为输入只能是null或 JS 对象对象会先经JSON.stringify序列化再json.Unmarshal成 rclone 的rc.Params其本质是 Params 类型即map[string]any方法路由rc.Calls.Get(method)在 全局注册表 中按路径查找Call。注册表由rc.Add(call)填充——loader.js 示例里的core/version即注册于 fs/rc/internal.go 的init()rc/noop同样在 fs/rc/internal.go 注册执行call.Fn(ctx, in)得到rc.Params输出非 nil 时经过rc.Reshape通过一轮 JSON 序列化/反序列化把输出归一为纯map[string]interface{}保证可安全转换为 JS 值最终js.ValueOf(out2)返回给浏览器。需要说明的两个源码内标记回调使用context.Background()并带有// FIXME注释函数注释中也有FIXME should this should return a promise so we can return errors properly?——因此错误目前是通过返回值内携带error与status字段来传递而非抛出 JS 异常loader.js 的注释同样点明了这一点If the output object has an error and a status then it is an error。错误对象的形状与状态码映射出错时errorValue返回如下结构与 fs/rc/params.go 中rc.Error生成的标准错误响应保持同构return js.ValueOf(map[string]interface{}{ status: status, error: err.Error(), input: in, path: method, })状态码映射规则为默认500 Internal Server Error当错误是fs.ErrorDirNotFound/fs.ErrorObjectNotFound时改为404 Not Found当错误是rc.ErrParamInvalid/rc.ErrParamNotFound时改为400 Bad Request。这与 rclone HTTP RC 服务端的行为一致方便 Web 端用同一套错误处理逻辑。rc 方法体系WASM 与 HTTP 共用同一套注册机制理解本目录的关键在于WASM 库暴露的并不是私有 API而是与rclone rcd/--rc完全相同的 rc 注册表。每个Call含Path方法名、Fnfunc(ctx, in Params) (out Params, err error)、NoAuth是否免鉴权等字段WASM 路径下没有 HTTP 鉴权环节NoAuth等属性不影响调用但方法集合完全一致。以示例中的core/version为例其 Help 列出了version、decomposed、isGit、os、arch、goVersion等返回字段——浏览器控制台打印的输出即包含这些键。此外rclone 全局 rc 相关配置--rc、--rc-addr默认localhost:5572、--rc-enable-metrics等见 fs/rc/rc.go属于 HTTP 服务端模式WASM 库路径不启动 HTTP 服务器这些选项在浏览器场景下不生效这也是两种使用 rc 的方式的本质区别一种是进程内库调用一种是网络请求。上手步骤与限制说明完整上手路径在 fs/rc/js/ 目录下操作make serve该命令先编译rclone.wasm再启动静态服务器随后浏览器打开 http://localhost:3000/在开发者控制台查看core/version、rc/noop、operations/mkdir、operations/list四个示例输出的对象。适用前提与限制需要 Go 工具链编译产物为原生go build输出未使用 TinyGo 等第三方工具当前示例仅引入backend/memory后端见 main.go 的导入注释示例数据全部落在:memory:刷新页面即丢失rc 调用是同步式的 JS 函数返回错误靠返回值中的status/error字段判断如上文FIXME注释所述所有 rc 方法均可通过同一注册表机制被发现与扩展——operations/*、sync/*等已在默认构建中可用。这套 rclone as a library in the browser 的最小可用参考实现为在 Web 前端直接执行 rclone 的目录创建、列举、同步等操作提供了完整的编译与调用样板。【免费下载链接】rclonersync for cloud storage - Google Drive, S3, Dropbox, Backblaze B2, One Drive, Swift, Hubic, Wasabi, Google Cloud Storage, Azure Blob, Azure Files, Yandex Files项目地址: https://gitcode.com/GitHub_Trending/rc/rclone创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考