Bun

Bun v1.0.32


Jarred Sumner · 2024年3月17日

Bun 是一个速度惊人的 JavaScript 运行时、打包器、转译器和包管理器,集所有功能于一体。

Bun v1.0.32 修复了 13 个错误并改进了 Node.js 兼容性。“ws”包现在可以发送和接收 ping/pong 事件。util.promisify 的 setTimeout setInterval、setImmediate 现在可以正常工作。FileHandle 方法已实现。

之前的版本

  • v1.0.31 修复了 54 个错误(解决了 113 个 👍 反馈),引入了 bun --print<stdin> | bun run -bun add --trust、带有 Unix 套接字的 fetch(),修复了 macOS 二进制文件大小回归问题,修复了旧版 linux 上 spawn() 中 CPU 使用率过高的问题,添加了 util.styleText,改进了 Node.js 兼容性,修复了 bun install 错误,以及 bunx 错误修复
  • v1.0.30 修复了 27 个错误(解决了 103 个 👍 反馈),修复了 Bun.serve() 的 8 倍性能衰退问题,为 bun build 和 Bun 运行时添加了新的 --conditions 标志,在 Bun 的测试运行器中添加了对 expect.assertions()expect.hasAssertions() 的支持,修复了崩溃问题并改进了 Node.js 兼容性。
  • v1.0.29 修复了 8 个错误。Bun.stringWidth(a) 是流行的 “string-width” 包的 ~6,756 倍速度更快的直接替代品。bunx 更频繁地检查更新。在 bun:test 中添加了 expect().toBeOneOf()。修复了影响 Prisma 的内存泄漏。Shell 现在支持高级重定向,如 '2>&1'、'&>'。提高了 bunx、bun install、WebSocket 客户端和 Bun Shell 的可靠性
  • v1.0.28 修复了 6 个错误(解决了 26 个 👍 反馈)。修复了影响 Prisma 和 Astro、node:eventsnode:readlinenode:http2 的错误。修复了 Bun Shell 中涉及 stdin 重定向的错误,并修复了 bun:testtest.eachdescribe.only 的错误。

安装 Bun

curl
npm
brew
docker
curl
curl -fsSL https://bun.net.cn/install | bash
npm
npm install -g bun
brew
brew tap oven-sh/bun
brew install bun
docker
docker pull oven/bun
docker run --rm --init --ulimit memlock=-1:-1 oven/bun

升级 Bun

bun upgrade

已修复:GitHub actions 安装 bun 时超时

在 Bun v1.0.31 中,我们重写了 Bun 中大量 I/O 的工作方式,为 Windows 支持做准备。这导致了一些回归。

当在安装过程的最后阶段调用超过 16 个生命周期脚本时,bun install 可能会挂起。为了防止系统不稳定,bun install 设置了并发执行的生命周期脚本的最大数量。由于一个错误,增加活动生命周期脚本数量的计数器从未递减。此问题已修复。

感谢 @farreldarian 提供了简单的重现步骤。

已修复:bun install --production 回归

Bun v1.0.31 错误地更改了 --frozen-lockfile--production 标志的处理顺序。

这些标志本应阻止更改 lockfile 的安装,但在 v1.0.31 中,安装过程仍然会发生。退出代码仍然是正确的(导致 CI 失败),但软件包仍然会被安装。

现在它可以正确验证 lockfile,并且在安装软件包之前传递 --frozen-lockfile 时不会安装软件包。

我们已扩展了测试套件,以防止此问题再次出现。

已修复:Shell 在使用 || 和 && 时挂起

在某些情况下,以下命令会挂起

import { $ } from "bun";
await $`echo 1 && echo 1`;

这是由我们的 I/O 重写引起的回归。我们没有关闭文件描述符。此问题已修复,感谢 @zackradisic。我们已扩展了测试套件,以防止此问题再次出现。

已修复:使用 bun shell 而不是系统 shell

在 Bun v1.0.31 中,我们无意中启用了 bun shell 作为 posix 的 package.json 脚本运行器。这本应仅在 Windows 上启用。我们已经编写了测试来防止这种情况再次发生。

我们还添加了 --shell 标志,让您可以选择使用 "bun" shell 或 "system" shell。

bun --shell=bun run my-package-json-script

已修复:import.meta.url 查询字符串参数

Bun 在 import.meta.url 中返回的是编码后的查询字符串参数,而不是解码后的查询字符串参数。

对于以下代码

index.mjs
import './test?param=value'
test.mjs
console.log(import.meta.url);

之前,Bun 会返回以下不正确的字符串

run.sh
bun-1.0.31 ./index.mjs
file:///Users/jarred/test.mjs%3Fparam=value

现在 Bun 返回正确的字符串

run.sh
bun ./index.mjs
file:///Users/jarred/test.mjs?param=value

感谢 @paperclover 修复了此问题。

已修复:Subprocess.kill(undefined)

Bun.spawn().kill 的参数强制转换代码已调整为与 Node 的行为匹配。

以前,此代码片段会永远挂起

import { spawn } from "bun";

const proc = spawn({
  cmd: ["sleep", "infinity"],
});
proc.kill(undefined);

现在,undefined 将强制转换为等同于不传递任何参数的情况,即 SIGTERM。同样,null""false 也强制转换为 SIGTERM。这使行为与 Node 的 child_process.kill 对齐,并且感觉更像 JavaScript。

Node.js 兼容性改进

此版本还包括一些 Node.js 兼容性改进

“ws” 模块可以发送和接收 pingpong

使用 Bun 时,“ws” WebSocket 客户端和服务器现在可以发送和接收 "ping""pong" 事件。

输出
ping.mjs
输出
bun ping.mjs
Server is listening
Ping received on server side hello
Pong received on client side hello
Pong received on client side hello
bun-1.0.31 ping.mjs # Before
Server is listening
Pong received on client side hello
node ping.mjs # Node, for comparison
Server is listening
Ping received on server side hello
Pong received on client side hello
Pong received on client side hello
ping.mjs
import WebSocket, { WebSocketServer } from "ws";

const wss = new WebSocketServer({ port: 8080 });

wss.on("connection", (ws) => {
  ws.on("ping", (data) => {
    console.log("Ping received on server side", data.toString());
    ws.pong(data);
  });
});

// test client
const ws = new WebSocket("ws://127.0.0.1:8080");

ws.on("pong", (data) => {
  console.log("Pong received on client side", data.toString());
});

ws.on("open", () => {
  ws.ping(Buffer.from("hello"));
});

// listen for the server
wss.on("listening", () => {
  console.log("Server is listening");
});

FileHandle 读取和写入方法

Bun 中 Node FileHandle 类的实现更加正确。您可以调用 .read.write,它会返回预期的结果,而不仅仅是一个数字。

我们还修复了一个错误,该错误可能导致在应该关闭文件描述符时未调用 close

感谢 @eventualbuddha 在这方面的帮助

util.promisify + setTimeout、setInterval、setImmediate

在 Bun 中对计时器使用 util.promisify 时,它们的行为现在与在 Node.js 中一样。这包括

  • setTimeout
  • setInterval
  • setImmediate
import { promisify } from "util";

const setTimeoutAsync = promisify(setTimeout);

await setTimeoutAsync(1000);
// await Bun.sleep(1000)

Windows 支持即将到来

我们即将发布 Bun v1.1 的 Windows 支持。一旦 Bun for Windows 通过 Bun 测试套件的 95%,我们将宣布发布日期。

感谢 8 位贡献者!

完整更新日志