🎉 2018 版 Rust 正式发布,Rust 和 WebAssembly 的初始开发故事也随之而来!🎉

为了看看我们走了多远,让我们回顾一下一年前的 Rust 和 WebAssembly 故事:rustc 可以为你生成 WebAssembly 二进制文件,但仅此而已。至于与 JavaScript 的通信,你必须自己处理原始的 wasm 导入和导出。这意味着你只能来回传递 32 位和 64 位整数和浮点数。无法来回传递 Rust 结构体、JavaScript 对象、字符串或切片。而将你的库的 .wasm 分发出去,以便其他下游项目可以依赖它?祝你好运。

虽然很 清楚 Rust 和 WebAssembly 拥有巨大的潜力,但没有人确定这到底意味着什么。因此,当 Rust 和 WebAssembly 领域工作组成立时,我们团结起来,将这一共同愿景变为现实。

将 Rust 编译为 WebAssembly 应该是为 Web 提供快速可靠代码的最佳选择。

随着我们想法的演变,我们提炼出另一个核心价值观。

Rust 和 WebAssembly 在这里是为了增强你的 JavaScript,而不是取代它。

就像 Rust 在原生目标上与 C 库和调用约定集成一样,它也应该与 Web 上的 JavaScript 和 HTML5 API 相处融洽。你不应该重写整个 Web 应用程序或 JavaScript 库。如果这意味着你必须从头开始,我们就无法实现我们对 Rust 和 wasm 的愿景;这将不切实际。

鉴于这些共同的价值观和愿景,我们为 Rust 和 WebAssembly 生态系统、工具链和工作流程在 Rust 2018 发布时应该是什么样子设定了目标。

目标:☑ 零成本 JavaScript 交互

Rust 通过利用零成本抽象来实现快速表达能力强的代码。我们希望将这一原则应用于整个 JS 交互基础设施。是的,你可以编写自己的样板代码来将 DOM 节点传递给 Rust 生成的 wasm,但你不应该这样做,提供的基础设施应该与你手动编码时一样快。如果你调用 IndexedDB API,这不会使你的 .wasm 二进制文件膨胀,其中包含未使用的 Web GL 函数绑定。

我们创建了 wasm-bindgen 作为零成本 JavaScript 交互的基础。 wasm-bindgen 促进 JavaScript 和 WebAssembly 之间的通信,并生成你原本需要自己编写的粘合代码。在 wasm-bindgen 之上,我们构建了 js-sys(对 ECMAScript API 的原始绑定)和 web-sys(对 Web API 的原始绑定).

使用 wasm-bindgen 生态系统,我们可以轻松高效地

  • 从我们 Rust 生成的 wasm 库中导出丰富的 API,以便它们可以从 JavaScript 中调用,以及
  • 将 JavaScript 和 Web API 导入到我们 Rust 生成的 wasm 中。

所有这些都以零成本的方式完成。

此外,wasm-bindgenWebAssembly 主机绑定提案 向前兼容。主机绑定将删除位于我们的 wasm 函数和 DOM 方法之间的微小的、生成的 JavaScript shim 函数。最终,主机绑定有望实现比 JavaScript 甚至更快的 DOM 访问速度,因为调用可以静态验证一次,而不是每次动态检查。

目标:☑ 将 Rust 生成的 Wasm 作为 NPM 库分发

出色的集成不仅仅是关于在 Rust 生成的 WebAssembly 和 JavaScript 之间导出和导入功能。它还适合 JavaScript 的分发机制,而这方面很大一部分是 NPM.

我们 构建了 wasm-pack,以便从你的 Rust 和 WebAssembly 代码中轻松创建和发布 NPM 包。以前,根本没有关于共享 Rust 生成的 wasm 模块的故事。现在,只需要

wasm-pack publish

目标:☑ 让开发者快速提高生产力

我们编写了 一本 Rust 和 WebAssembly 书籍,教你使用 Rust 进行 WebAssembly 开发的所有来龙去脉。它包含 一个教程,你将在其中构建 Conway 生命游戏的实现,然后你将学习为无头浏览器编写测试,在出现问题时调试 wasm 代码,以及如何诊断缓慢的代码路径,然后对其进行加速。

我们意识到,在 cargorustc 生成初始 .wasm 二进制文件之后,你想要运行许多“构建后”工具。为了提高可用性和开发人员生产力,我们扩展了 wasm-pack 的作用,使其不仅创建和发布 NPM 包,还协调所有这些任务。 wasm-pack 将管理你的 wasm-bindgen CLI 二进制文件,并自动为你安装浏览器的 WebDriver 客户端。

例如,想要在无头 Firefox 浏览器中运行测试?只需运行

wasm-pack test --headless --firefox

无需费力地尝试安装和配置任何东西!

最后,我们认识到,最初设置你的 Rust 和 WebAssembly 项目涉及一些新用户没有准备好的样板代码和配置,而有经验的用户也不想浪费时间。因此,我们为不同的用例创建了各种项目模板,以便你可以立即上手。

  • wasm-pack-template 用于使用 Rust 和 Wasm 创建 NPM 库。
  • create-wasm-app 用于创建构建在 Rust 生成的 wasm NPM 库之上的 Web 应用程序。
  • rust-webpack-template 用于使用 Rust、WebAssembly 和 Webpack 捆绑器创建完整的 Web 应用程序。
  • rust-parcel-template 用于使用 Rust、WebAssembly 和 Parcel 捆绑器创建完整的 Web 应用程序。

目标:☑ Rust 生成的 Wasm 应该是可测试和可调试的

我们认识到,测试和调试基础设施是创建可靠代码和开发人员生产力的关键。

默认情况下,wasm 无法记录任何恐慌或错误,因为它没有任何“系统调用”或 I/O 功能。你必须自己添加这些东西的导入,然后使用适当的函数实例化模块。为了解决这个问题,并确保恐慌始终可调试,我们创建了 console_error_panic_hook crate,它将恐慌消息重定向到浏览器的开发者工具控制台。

虽然你始终可以在原生目标上运行正常的 #[test] 来获得可移植的、与平台无关的代码,但这不足以测试你的库与 DOM、异步 JavaScript Promise 或事件处理程序的交互。因此,我们创建了 wasm-bindgen-test 基础设施,并使用 wasm-pack test 使安装和配置无头浏览器和 Node.js 测试所需的二进制文件变得轻而易举。

我们还发现,使用 WebAssembly 诊断代码大小来自哪里可能很困难。我们想知道哪些函数调用了另一个函数,并导致它被包含在 .wasm 二进制文件中,因此我们创建了 WebAssembly 的 Twiggy🌱 代码大小分析器.

 Shallow Bytes │ Shallow % │ Retaining Paths
───────────────┼───────────┼───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
           152 ┊     5.40% ┊ wee_alloc::alloc_with_refill::hb32c1bbce9ebda8e
               ┊           ┊   ⬑ func[2]
               ┊           ┊       ⬑ <wee_alloc::size_classes::SizeClassAllocPolicy<'a> as wee_alloc::AllocPolicy>::new_cell_for_free_list::h3987e3054b8224e6
               ┊           ┊           ⬑ func[5]
               ┊           ┊               ⬑ elem[0]
               ┊           ┊       ⬑ hello
               ┊           ┊           ⬑ func[8]
               ┊           ┊               ⬑ export "hello"

#RustWasm2019

我们所有的目标都集中在我们能够与 2018 版一起交付的事情上。但现在 2018 版已经发布,是时候考虑我们希望在 2019 年及以后实现的目标了。

这就是你需要发挥作用的地方!

遵循更大的 Rust 项目的 传统,我们要求社区撰写博客文章,回顾 2018 年的 Rust 和 WebAssembly,并提出 2019 年 Rust 和 WebAssembly 的目标和方向。我们会阅读所有内容,然后为 Rust 和 WebAssembly 领域工作组的 2019 年路线图提出一个 RFC

把你对任何你喜欢的写作平台的想法写下来。它可以是

  • 你的个人或公司博客
  • 一个 GitHub gist
  • 一篇 Medium 文章
  • 任何你喜欢的其他平台

我们正在寻找关于许多不同主题的文章

  • 社区计划的想法
  • 工具增强
  • 生态系统和库需求
  • 文档改进
  • 与 Rust 和 Wasm 相关的任何其他内容!

使用 #RustWasm2019 标签 推特你的文章,或在 这个 github 问题 上发布链接。我们会将每个人写的所有内容汇总到这篇博客的另一篇大型文章中。然后,Rust 和 WebAssembly 核心工作组团队将阅读所有内容,并为工作组的 2019 年路线图编写一个 RFC!这个 RFC 将遵循我们正常的 RFC 流程,每个人都有机会讨论它、改进它,并帮助完善它。

初步时间线

  • 现在到 1 月 15 日:分享你的 #RustWasm2019 文章,阅读他人的文章,讨论它们,互相交流想法。
  • 1 月底:我们将正式提出 2019 年路线图 RFC,然后与社区一起完成 RFC 流程。
  • 2 月底:我们的目标是在 2 月底之前就 2019 年路线图达成共识,并合并 RFC。

感谢 2018 年的精彩时光!💖

感谢所有在 2018 年为 Rust 和 WebAssembly 做出贡献的人!(如果我们遗漏了列表中的任何人,我们表示歉意!)

  • 0xazure
  • Aaron Turon
  • Aditya Arora
  • Aidan Hobson Sayers
  • Aleksey Kladov
  • Alex Crichton
  • Alex Macleod
  • Alexander Kryvomaz
  • Alfie John
  • Anders Pitman
  • Andrew Champion
  • Andrew Chin
  • 安迪·贝尔
  • 安娜·博古斯
  • 安东·达尼尔金
  • 阿什利·威廉姆斯
  • 本·梅里特
  • 本杰明·坎普曼
  • 布利克斯
  • 布拉德利·斯派斯
  • 卡梅伦·塔加特
  • 卡米尔·TJHOA
  • 奇内杜·弗朗西斯·恩瓦菲利
  • 克里斯·戈勒
  • 克里斯·科洛丁
  • 克里斯蒂安·布尔乔
  • 克里斯托弗·莱恩·欣森
  • Cldfire
  • 科宾·尤塞尔顿
  • 科里·法威尔
  • 克雷格·迪塞尔科恩
  • 丹·福克勒
  • 丹·里夫斯
  • 丹尼尔·戈拉洪
  • 丹尼尔·埃斯波斯蒂
  • 丹妮尔·法姆
  • 达伦·曾
  • 大卫·弗莱姆斯特罗姆
  • 大卫·麦克尼尔
  • 大卫·奥康纳
  • DebugSteven
  • 德米特里·涅姆科夫
  • 德米特里·卡希特辛
  • 爱德华·基文科
  • 埃里克·特里泽拉尔
  • 埃里卡·克洛斯
  • 埃文·肖
  • 菲利克斯·舒特
  • 弗洛里安·吉尔切
  • 弗兰克·哈桑纳巴德
  • 弗雷泽·麦克林
  • 格尔盖伊·纳吉
  • 盖伊·沃尔德曼
  • 亨德里克·索利希
  • 亨里克·斯约霍
  • 赫尔曼·J·拉德克三世
  • Hidehito Yabuuchi
  • 伊恩·杜克
  • 伊恩·麦克因泰尔
  • 英格瓦尔·斯捷潘扬
  • 约阿尼斯·瓦拉萨基斯
  • 伊万·恩德林
  • J. 莱恩·斯蒂内特
  • 杰门·马兹
  • 杰米·凯尔
  • 扬·威廉·亨克尔
  • 扬-埃里克·雷迪格
  • 扬尼克·凯耶
  • 杰森·戴维斯
  • 杰森·沃尔格穆斯
  • 耶斯珀·哈坎森
  • 吉姆·布兰迪
  • 乔尔·加兰特
  • 约翰·霍夫曼
  • 约翰内斯·亨宁格
  • 约翰·刘易斯
  • 乔纳斯·特罗尔维克
  • 乔纳森·金斯顿
  • 乔纳森·桑德奎斯特
  • 乔什·特里普莱特
  • 约书亚·利鲍-费瑟
  • 约书亚·希尔德
  • 约斯马尔·迪亚斯
  • 若昂·卢卡斯·卢切塔
  • 朱利叶斯·拉科
  • 黄俊杰
  • 卡塔琳娜·费
  • 凯文·霍夫曼
  • 基里尔·布拉托夫
  • 凯尔·林
  • 拉切扎尔·莱切夫
  • 劳伦蒂乌·尼古拉
  • 李戈·庄
  • LongYinan
  • 卢克·瓦格纳
  • 麦肯齐·克拉克
  • Mackiovello
  • 马纳斯·卡雷卡
  • 马尔辛·巴拉涅茨基
  • 马里奥·雷德
  • 马克·安德鲁·罗伯茨
  • 马克·欣茨
  • 马库斯·斯坦格
  • 梅森·斯塔尔莫
  • 马蒂亚斯·因索拉尔德
  • 马特·哈里森
  • 马特·豪厄尔
  • 马特·克雷
  • 马特·朗
  • MaxD / vj userZero
  • MaxXor
  • 迈克尔·加托齐
  • 迈克尔·格拉豪瑟
  • 迈克尔·霍夫曼
  • Mirclus
  • 内森·弗罗伊德
  • 尼克·菲茨杰拉德
  • 尼克·格拉夫
  • 尼古拉·沃尔夫
  • 诺亚·莱门
  • 努米尔·普蒂普
  • OJ Kwon
  • 帕斯卡尔·布兰特
  • 帕斯卡尔·赫特莱夫
  • 帕特·希基
  • 彼得·特罗特曼
  • R. 安德鲁·奥哈纳
  • 拉胡尔·夏尔马
  • 拉尔夫·吉尔斯
  • 蕾妮·库伊
  • 里卡多·安布罗吉
  • 理查德·多德 (dodj)
  • 罗伯特·马森
  • 罗伯托·胡埃塔斯
  • 张荣建
  • 鲁本·施密德迈斯特
  • 瑞安·莱维克
  • 萨拉尔·卡博利
  • 圣地亚哥·帕斯托里诺
  • 佐藤·阿美弥
  • 斯科特·约翰逊
  • 塞巴斯蒂安·科隆
  • 森迪尔·库马尔·N
  • 谢尔盖·佩皮亚金
  • 沙拉德·钱德
  • 桑尼·斯克罗金
  • 索菲·阿尔珀特
  • 斯宾塞·威尔逊
  • 斯特凡·诺瓦克
  • 斯特凡·齐默尔曼
  • 斯特凡·雷纳图斯
  • 斯特凡·沃尔斯基
  • 史蒂夫·克拉布尼克
  • 斯文·索勒
  • T. 长泽
  • 何涛
  • 泰德·米尔查雷克
  • Theemathas Chirananthavat
  • 蒂亚戈·蓬特斯
  • 托马斯·艾辛格
  • 蒂姆·瑞安
  • 托比亚斯·比涅克
  • Tomohide Takao
  • 托马斯·胡贝尔鲍尔
  • 泰勒·莱恩
  • 泰勒·威尔科克
  • 威廉·伦德斯特
  • YUyz
  • 约书亚·伍伊茨
  • 尤里·德伦迪克
  • 尤瓦尔·科哈维
  • 扎卡里·皮尔斯
  • 扎克·皮尔斯
  • afdw
  • alkahest
  • andy-bell
  • arjunyel
  • ashley williams
  • belfz
  • bokuweb
  • bspeice
  • csmoe
  • data-pup
  • dependabot[bot]
  • frankhassanbad
  • gaurikholkar
  • gnzlbg
  • huangjj27
  • janczer
  • johnthagen
  • kohensu
  • konstin
  • kryptan
  • kzvi
  • limira
  • na-g
  • pup
  • robert masen
  • robertdurst
  • sarahmeyer
  • sepiropht
  • sigmaSd
  • soryrawyer
  • teovoinea
  • toversus
  • twilco
  • xeqlol