跳到主要内容
Deno in 2024

Deno 在 2024 年

在 2024 年,Deno 团队在简化编程的愿景上取得了显著进展。我们推出了备受期待的 Deno 2,它提供了与 Node 和 npm 的向后兼容性,为工具链添加了依赖管理,并通过 monorepo 和工作区支持扩展了灵活性。以下是 2024 年值得注意的技术改进摘要

让我们在下面更深入地了解这些更新。

与 Node 和 npm 的向后兼容性

在 2022 年,我们的调查回复表明,能够在 Deno 中使用 npm 包非常重要。经过两年勤奋的工作,随着 Deno 2 的发布,我们很高兴地宣布 Deno 提供了与 Node 和 npm 的向后兼容性。

Deno 实现向后兼容性的一些关键更新包括理解 package.json,移除全局变量 window 并添加 process,使 “自带 Node 模块” 功能成为默认设置,以及对 node: 内置模块和更多内容的数十个错误修复。借助 Deno 2,您不仅可以在 Deno 中运行现有的 Node 项目,还可以导入和使用 npm 包,例如 playwrightprismasqlite3duckdbgRPC。最重要的是,Deno 2 支持 JavaScript 框架,例如 Next.js、Astro、Remix、Qwik、Solid 等。

Deno 2 is backwards compatible with Node and npm

Deno 2 向后兼容 Node 和 npm,使您可以使用您首选的 JavaScript 框架。观看完整的 Deno 2 发布公告视频。

尽管我们坚信 ES 模块是 JavaScript 的未来,但许多遗留项目和库都依赖于 CommonJS。在 2024 年,我们改进了我们的 CommonJS 支持。Deno 可以运行和导入扩展名为 .cjs 的 CommonJS 文件,并在处理 CommonJS 问题时提供更具描述性的错误。

最后,为了在您的 Deno 项目中实现更大的灵活性,我们添加了 monorepo 和工作区支持。Deno 工作区也理解 npm 工作区,这意味着您可以创建一个混合的 Deno-npm monorepo,其成员可以拥有 package.jsondeno.json。您甚至可以使用 deno publish 将工作区成员发布到 JSR,而无需手动弄清楚以什么顺序发布它们(请参阅 Deno 标准库 示例)。

内置、高性能的依赖管理

从 Deno 2 开始,Deno 附带了一个包管理器,并添加了以下新子命令:deno installdeno adddeno remove。如果您使用过 npm,这些子命令会很熟悉,但它们速度更快:deno install 在冷缓存情况下比 npm 快 15%,在热缓存情况下快 90%。

Deno install performance benchmarks.

这些包管理命令可以根据提供的说明符或包是否在 package.jsondeno.json 中找到,从 npm 或 JSR 拉取/删除包。

为了扩展对需要执行 pre 或 post-install 脚本的 npm 包的支持,我们还添加了 对 npm 生命周期脚本的支持,并添加了新标志 --allow-scripts

deno install --allow-scripts=npm:duckdb

最后,为了更轻松地在更大的开发团队中共享内部模块,我们添加了 私有 npm 注册表支持。它们的工作方式与在 Node 和 npm 中完全相同:使用 .npmrc 文件

// .npmrc
@mycompany:registry=http://mycompany.com:8111/
//mycompany.com:8111/:_auth=secretToken

JSR:一个现代、开源的 JavaScript 注册表

今年,我们推出了一个新的 JavaScript 注册表JSR。它原生支持 TypeScript(您可以将模块作为源代码发布),处理跨运行时和环境的模块加载,从 JSDoc 风格的注释自动生成文档,并且可以与类似 npm/npx 的系统一起使用。

由于 TypeScript 源代码可以直接上传到 JSR,因此它对代码有深入的了解。这为发布和使用模块都实现了更流畅、无缝的开发者体验。要了解幕后的一切,请阅读我们关于 我们如何构建 JSR 的文章。

这是一个并排比较将包发布到 npm 与发布到 JSR 的视频。

使用 deno publish 将模块发布到 JSR 非常简单,您甚至可以使用 deno init --lib 快速搭建 JSR 模块。

Project initialized

Run these commands to get started

  # Run the tests
  deno test

  # Run the tests and watch for file changes
  deno task dev

  # Publish to JSR (dry run)
  deno publish --dry-run

尽管 JSR 是 Deno 团队构建的,但它是为更大的 JavaScript 社区设计的。我们目前正在努力为 JSR 建立一个开放的管理机构。如果您有兴趣并想了解更多信息,请查看 JSR discord加入我们的双周办公时间,我们在那里回答社区问题并分享 JSR 路线图。

更快、更小、更简单的来自 JavaScript 的跨平台编译二进制文件

自 Deno v1.6 以来,deno compile 使开发人员能够将 JavaScript 和 TypeScript 程序转换为可在所有主要平台上运行的单个独立二进制文件 — 无需依赖项,无需额外安装。这意味着简化的部署和更快的启动。与 Node 的 8 步编译过程 不同,deno compile 只是一个命令。

在过去的一年中,我们对 deno compile 进行了重大改进,例如 将编译后的二进制文件缩小了最多 50%,添加了用于软件验证的代码签名、Windows 图标支持和 资源捆绑。此外,使用 deno compile 创建的程序还可以使用 V8 代码缓存以获得更快的启动时间。通过这些更新,您现在可以将完整的应用程序 (例如 HTML/JS/CSS 游戏)编译为原生桌面二进制文件

为了演示使用 deno compile 带来的性能提升,以下是一个编译 npm 的示例

deno compile -A npm:npm

在我们的观察中,Deno 编译的 npm 二进制文件比常规 npm 运行速度快约 1.9 倍

# hyperfine "./npm -v" "npm -v"
Benchmark 1: ./npm -v
  Time (mean ± σ):      40.1 ms ±  2.0 ms    [User: 37.7 ms, System: 5.3 ms]
  Range (min … max):    38.9 ms … 51.8 ms    71 runs

Benchmark 2: npm -v
  Time (mean ± σ):      75.2 ms ±  7.6 ms    [User: 59.1 ms, System: 9.0 ms]
  Range (min … max):    69.2 ms … 105.0 ms   40 runs

Summary
  ./npm -v ran
    1.87 ± 0.21 times faster than npm -v

我们将继续迭代和改进 deno compile,例如支持编译完整堆栈框架等。

使用 deno serve 构建更快、更简单的 Web 服务器

构建 Web 服务器是 Deno 的常见用例,去年我们在其性能和可用性方面都取得了显著改进。我们重新设计了 Deno.serve() API,使其速度提高了 8-15%

在 Deno 中编写服务器也更容易。我们还添加了 命令 deno serve,允许您声明式地编写服务器

export default {
  fetch(request) {
    return new Response("Hello world");
  },
};
$ deno serve server.ts
deno serve: Listening on http://localhost:8000/
$ curl http://localhost:8000/
Hello world

deno serve 还通过 --parallel 标志支持多线程服务器,从而可以在多个 CPU 核心之间自动进行负载均衡,并且同样易于使用。

您可以使用 deno init --serve 选项 在几秒钟内启动一个新服务器。Deno 还添加了使用 satisfies Deno.ServeDefaultExport 对服务器入口点文件进行类型检查 的能力。

Deno 在 AWS Lambda 上表现出色

Deno 致力于构建最快、性能最高的 JavaScript 和 TypeScript 运行时,去年我们朝着这个目标迈出了重要一步。我们通过添加 V8 代码缓存在快照时间预热引导初始化 改进了启动时间。

当 Deno 在无服务器环境中使用时(Deno 通常在生产环境中使用),我们在 Deno 中也进行了重大的性能改进。Deno 为 DENO_DIR 中的 SQLite 数据库添加了预写日志 (WAL) 日志,从而改进了代码缓存、启动时间和冷启动。为了比较在无服务器环境中的性能,我们发布了 AWS Lambda 上 JavaScript 运行时的冷启动基准测试,其中包括我们的方法以及一些最大化性能的技巧。

Cold start benchmarks for running an identical Hono URL shortener app on AWS Lambda.

在 AWS Lambda 上运行相同的 Hono URL 缩短器应用程序的冷启动基准测试。

去年,Deno 的整体性能故事还有许多其他改进。尽管基准测试永远无法揭示全部情况,但它们可以深入了解运行时擅长的地方。以下是 2.0 版本中的一些基准测试,希望能提供更好的想法。

Performance benchmarks for Deno 2

来自我们的 Deno 2 公告 的性能基准测试。请参阅每个图表下方的链接以获取更多详细信息和可重复的步骤。

Temporal API 和 Wasm 导入

Temporal API 旨在解决 JavaScript 中 Date 对象的局限性和复杂性,目前正在所有主要的 JavaScript 引擎中积极实现。您已经可以在 Deno 中 使用 --unstable-temporal 标志 试用它。

虽然 WebAssembly (“Wasm”) 支持在 Deno 中一直可用,但我们的 2.1 版本将 Wasm 支持提升为一流,使导入 Wasm 模块就像导入任何其他模块或文件一样简单

// Now in Deno 2.1
import { add } from "./add.wasm";

console.log(add(1, 2));
// $ deno main.ts
// 3

现在,在 Deno 中加载 Wasm 模块的性能更高,因为它们是“模块图”的一部分,可以对其进行分析和缓存以加快使用速度。不仅如此,Deno 还了解导出 Wasm 模块,并且可以对它们在代码库中的使用进行类型检查。

随着越来越多的 Wasm 在 Web 上用于提高浏览器中的应用程序性能,我们将继续努力使在 Deno 中使用 Wasm 变得尽可能简单和快速。

使用 deno.json 做更多事情

编程应该很简单,这就是为什么我们将 Deno 构建为零配置且具有合理的默认值。但是,我们承认,较大的项目通常需要更复杂的设置,因此我们不断改进我们可选的 deno.json 配置文件,以满足这些需求,而不会牺牲易用性

这些改进有助于使 Deno 不仅对大型应用程序强大而灵活,而且对小型项目也简单易用。

Deno 标准库,已稳定

经过 4 年多、151 个版本和 4k 次提交后,Deno 标准库 终于稳定了。这个包含 40 多个经过严格审计的实用程序模块的集合涵盖了 JavaScript、Web 和通用数据操作中的广泛用途。最棒的是,这个库可以在所有 JavaScript 运行时和环境(如浏览器)中使用。

观看这个 3 分钟的视频,大致了解 Deno 标准库。

为了让您了解 Deno 标准库中可用的模块类型,以下是标准库模块及其在 npm 中的等效模块的部分列表

Deno 标准库模块 npm 包
@std/testing jest
@std/expect chai
@std/cli minimist
@std/collections lodash
@std/fmt chalk
@std/net get-port
@std/encoding rfc4648

有关可用软件包的完整列表,请访问 https://jsr.deno.org.cn/@std

值得注意的开源 Rust Crates

构建 Deno 意味着接触广泛的开源项目,我们为这些项目做出贡献,以扩展 Deno 的功能并优化性能。以下是一些 Rust Crates,开发人员可能会发现它们独立于 Deno 本身也很有用

  • rusty_v8:此库为 V8 的 C++ API 提供了高质量、零开销的 Rust 绑定。自从我们五年前首次发布它以来,它已经发布了近 150 个版本,并在 crates.io 上下载了超过 310 万次。去年,我们宣布 rusty_v8 已稳定且可用于生产环境
  • deno_semver:此 Rust crate 提供了用于解析、比较、验证和操作 npm 和 JSR 包使用的语义版本控制 (semver) 字符串的实用程序。
  • deno_npm:此 crate 是一个 npm 客户端,充当 Deno 和 npm 包生态系统之间的桥梁。此库以 Node.js 相同的方式解析 npm 模块,因此如果您正在编写 Rust 并希望与 npm 生态系统互操作,则此库非常有用。
  • deno-vite-plugin:此 Deno Vite 插件在 Vite 中启用 Deno 解析,允许您将 Deno 与 Vite 一起使用,以及从 JSR 和 HTTP 导入库到 Vite 中。
  • deno_cache_dir:此 TypeScript 模块提供对 Deno 缓存的访问,其逻辑与 Deno CLI 相同。其他几个 Deno 工具,例如 deno_graphdeno_docdntdeno_emit,都依赖此模块以与 Deno CLI 相同的方式访问和填充缓存。

Fresh、Deno Deploy、Subhosting

在我们发布 Deno 2 标志着一个重要的里程碑的同时,我们继续运营和迭代我们的无服务器计算平台 Deno Deploy,这是在云中运行任意 JavaScript/TypeScript 的最简单方式。

我们为 Deno Deploy 用户改进了入门流程,新的教程展示了使用 Deno 云原语入门有多么容易,以及 简化的项目创建流程,它可以自动检测框架并提供有关构建和部署步骤的更多透明度。我们还 让 Next.js 在 Deno Deploy 上工作了

我们还为用户提供了更灵活的使用 Deno Deploy 的方式。我们发布了 deployctl,Deno Deploy 的 CLI,它允许用户从终端创建、管理和观察您的部署。Web Cache API 支持 还使用户可以精细地控制其部署的性能。此外,我们还实施了 通过新的支出限额来保障云计费

我们的企业产品 Deno Subhosting 在过去一年中持续改进。我们添加了对 以编程方式管理自定义域和子域配置数据备份 的支持。如果您想了解更多关于您的产品如何在无需数月工程工作的情况下安全运行用户不受信任的代码的信息,请联系我们

最后,我们正在继续迭代我们的下一代、基于 islands 的全栈 Web 框架 Fresh,2.0 版本即将推出。(实际上,Fresh 2 已经以 beta 版本提供,文档和正式发布即将推出。如果您想访问 Fresh 2,请在 Discord 中告知我们。)这个下一个主要版本是对内部 API 的重大修改,但应该解锁创建可组合和模块化中间件的能力。敬请关注!

超越 Deno 2

去年,我们发布了 Deno 2,扩展了开发人员已经喜欢 Deno 的特性 — 它的简洁性、一体化工具链、内置 Web 标准 API 和 TypeScript 支持 — 使其在更广泛的项目和用例中更灵活和可用

  • 与 Node 和 npm 的向后兼容性
  • Monorepo 和工作区支持
  • 通过 JSR 和 npm 改进的包管理
  • 企业功能,例如 LTS 和 专用企业支持渠道
如果您错过了 — 我们的官方 Deno 2 视频公告。

今年,我们将专注于使 Deno 在生产场景中更加可靠和高效。例如,在我们的下一个小版本中,我们计划改进可观察性、跟踪和调试。我们还在努力提高 Deno 和我们的商业产品 Deno Deploy 的云性能,我们希望尽快详细介绍。

保持关注 — 在 BlueskyTwitterYouTubeDiscord 上关注我们。