{"slug": "bun-v1-3-7", "title": "Bun v1.3.7", "summary": "Bun v1.3.7 introduces significant performance improvements, including a 50% faster `Buffer.from()` for arrays, a JavaScriptCore engine upgrade, and upcoming optimizations for async/await, `Array.from()`, `string.padStart/padEnd`, and `array.flat()`. The update also adds ARM64 performance enhancements, Windows ARM64 JIT and interpreter support, and fixes several bugs, including a race condition in Web Workers and exception handling edge cases. Additionally, `fetch` now preserves HTTP header casing, and a new `Bun.wrapAnsi()` function provides native ANSI-aware text wrapping for CLI tools.", "body_md": "#### To install Bun\n\n```\ncurl -fsSL https://bun.sh/install | bash\nnpm install -g bun\npowershell -c \"irm bun.sh/install.ps1|iex\"\nscoop install bun\nbrew tap oven-sh/bun\nbrew install bun\ndocker pull oven/bun\ndocker run --rm --init --ulimit memlock=-1:-1 oven/bun\n```\n\n#### To upgrade Bun\n\n```\nbun upgrade\n```\n\n[Faster ](#faster-buffer-from-with-arrays)`Buffer.from()`\n\nwith arrays\n\n`Buffer.from()`\n\nwith arrays`Buffer.from()`\n\nis now up to **50% faster** when creating buffers from JavaScript arrays.\n\n``` js\nconst data = [1, 2, 3, 4, 5, 6, 7, 8];\nconst buf = Buffer.from(data); // ~50% faster\n```\n\nThis optimization bypasses unnecessary construction overhead and leverages JSC's internal array detection to use bulk copy operations for both integer and floating-point arrays.\n\n| Array size | Improvement |\n|---|---|\n| 8 elements | ~50% faster |\n| 64 elements | ~42% faster |\n| 1024 elements | ~29% faster |\n\n[JavaScriptCore upgrade](#javascriptcore-upgrade)\n\nBun's underlying JavaScript engine has been upgraded to the latest version of WebKit's JavaScriptCore, bringing performance improvements and bug fixes.\n\n[Faster async/await](#faster-async-await)\n\nIn the next version of Bun & Safari\n\n— Bun (@bunjavascript)\n\nasync/await gets 35% faster, thanks to[@Constellation][pic.twitter.com/XhUuiIwzRX][January 15, 2026]\n\n[Faster ](#faster-array-from-arguments)`Array.from(arguments)`\n\n`Array.from(arguments)`\n\nIn the next version of Bun & Safari\n\n— Bun (@bunjavascript)\n\nArray.from(set), Array.from(arguments), Array.from(map.keys()), Array.from(map.values()) gets up to 2x faster thanks to[@__sosukesuzuki][https://t.co/gC8ljFQBDI][January 15, 2026]\n\n[Faster string.padStart & string.padEnd](#faster-string-padstart-string-padend)\n\nIn the next version of Bun & Safari\n\n— Bun (@bunjavascript)\n\nstring.padStart(len, fill) & string.padEnd(len, fill) get up to 90% faster, thanks to[@__sosukesuzuki][https://t.co/TdJTfs6B5G][January 15, 2026]\n\n[Faster ](#faster-array-flat)`array.flat()`\n\n`array.flat()`\n\nIn the next version of Bun & Safari\n\n— Bun (@bunjavascript)\n\narray.flat() gets up to 3x faster, thanks to[@__sosukesuzuki][https://t.co/3Oll89bxGf][January 15, 2026]\n\n[ARM64 Performance Improvements](#arm64-performance-improvements)\n\nOn Apple Silicon and other ARM64 platforms, compound boolean expressions like `if (x === 0 && y === 1)`\n\nnow compile to more efficient conditional compare instruction chains (`ccmp`\n\n/`ccmn`\n\n), reducing branch mispredictions and code size.\n\nAdditionally, floating-point constants can now be materialized directly in registers using ARM64 vector instructions, avoiding unnecessary memory loads.\n\n[Windows ARM64](#windows-arm64)\n\nWe've added JIT & interpreter support for Windows ARM64 to JavaScriptCore. This was the main blocker for unblocking Windows ARM64 support in Bun. We don't yet support Windows ARM64 in Bun, but it's coming soon.\n\n[Bug Fixes](#bug-fixes)\n\n**Fixed:** Race condition in thread termination that could cause issues when using Web Workers**Fixed:** Exception handling edge cases where termination exceptions could be incorrectly cleared during iterator operations and promise handling**Fixed:** Functions loaded from bytecode cache now correctly respect JIT compilation thresholds instead of compiling immediately on first execution\n\n`fetch`\n\nnow preserves header case when sending HTTP requests\n\n`fetch`\n\nnow preserves header case when sending HTTP requestsHTTP headers are technically case-insensitive per RFC 7230, but many APIs expect specific casing. Previously, Bun would lowercase all headers when sending HTTP requests (e.g., `authorization`\n\ninstead of `Authorization`\n\n), which could break compatibility with services that require exact header names.\n\nNow, `fetch`\n\nand the `node:https`\n\nmodule preserve the original casing of headers exactly as you define them, matching Node.js behavior.\n\n```\n// Headers are now sent with their original casing\nawait fetch(\"https://api.example.com/data\", {\n  headers: {\n    \"Authorization\": \"Bearer token123\", // sent as \"Authorization\"\n    \"Content-Type\": \"application/json\", // sent as \"Content-Type\"\n    \"X-Custom-Header\": \"value\", // sent as \"X-Custom-Header\"\n  },\n});\n\n// Also works with the Headers object\nconst headers = new Headers();\nheaders.set(\"Content-Type\", \"text/plain\"); // sent as \"Content-Type\"\n```\n\n`Bun.wrapAnsi()`\n\nfor ANSI-aware text wrapping\n\n`Bun.wrapAnsi()`\n\nfor ANSI-aware text wrappingBun now includes `Bun.wrapAnsi()`\n\n, a native implementation of the popular [wrap-ansi](https://www.npmjs.com/package/wrap-ansi) npm package. It wraps text to a specified column width while preserving ANSI escape codes, making it ideal for CLI tools that need to handle colored or styled output.\n\n``` js\nconst text = \"\\x1b[31mThis is a long red text that needs wrapping\\x1b[0m\";\nconst wrapped = Bun.wrapAnsi(text, 20);\n// Wraps at 20 columns, preserving the red color across line breaks\n```\n\n[API](#api)\n\n```\nBun.wrapAnsi(text: string, columns: number, options?: {\n  // Break words longer than columns (default: false)\n  hard?: boolean;\n\n  // Wrap at word boundaries (default: true)\n  wordWrap?: boolean;\n\n  // Trim leading/trailing whitespace (default: true)\n  trim?: boolean;\n\n  // Treat ambiguous-width chars as narrow (default: true)\n  ambiguousIsNarrow?: boolean;\n\n}): string\n```\n\n[Features](#features)\n\n- Preserves ANSI escape codes (SGR colors/styles)\n- Supports OSC 8 hyperlinks\n- Respects Unicode display widths (full-width characters, emoji)\n- Normalizes carriage return newline to newline\n\n[Performance](#performance)\n\n`Bun.wrapAnsi`\n\nis **33–88x faster** than the `wrap-ansi`\n\nnpm package:\n\n| Benchmark | npm | Bun | Speedup |\n|---|---|---|---|\n| Short text (45 chars) | 25.81 µs | 685 ns | 37x |\n| Medium text (810 chars) | 568 µs | 11.22 µs | 50x |\n| Long text (8100 chars) | 7.66 ms | 112 µs | 68x |\n| Hard wrap colored | 8.82 ms | 174 µs | 50x |\n| No trim long | 8.32 ms | 93.92 µs | 88x |\n\n[Markdown CPU Profile Output](#markdown-cpu-profile-output)\n\nBun's built-in CPU profiler now supports a `--cpu-prof-md`\n\nflag that generates profiling data in Markdown format, making it easy to share profiles on GitHub or analyze them with LLMs.\n\n```\n# Generate markdown profile only\nbun --cpu-prof-md script.js\n\n# Generate both Chrome DevTools JSON and markdown formats\nbun --cpu-prof --cpu-prof-md script.js\n```\n\nThe markdown output includes:\n\n**Summary table** with duration, sample count, and interval**Hot functions** ranked by self-time percentage**Call tree** showing total time including children**Function details** with caller/callee relationships**File breakdown** showing time spent per source file\n\nAll existing flags work with the new format:\n\n`--cpu-prof-name`\n\nfor custom filenames`--cpu-prof-dir`\n\nfor custom output directories\n\n[Heap Profiling with ](#heap-profiling-with-heap-prof)`--heap-prof`\n\n`--heap-prof`\n\nBun now supports heap profiling via new CLI flags, making it easier to diagnose memory leaks and analyze memory usage in your applications.\n\n```\n# Generate V8-compatible heap snapshot (opens in Chrome DevTools)\nbun --heap-prof script.js\n\n# Generate markdown heap profile (for CLI analysis with grep/sed/awk)\nbun --heap-prof-md script.js\n\n# Specify output location\nbun --heap-prof --heap-prof-dir ./profiles --heap-prof-name my-snapshot.heapsnapshot script.js\n```\n\nThe `--heap-prof`\n\nflag generates `.heapsnapshot`\n\nfiles that can be loaded directly into Chrome DevTools for visual analysis. The `--heap-prof-md`\n\nflag generates a markdown report optimized for command-line analysis:\n\n```\n## Summary\n\n| Metric          |    Value |\n| --------------- | -------: |\n| Total Heap Size | 208.2 KB |\n| Total Objects   |     2651 |\n| GC Roots        |      426 |\n\n## Top 50 Types by Retained Size\n\n| Rank | Type        | Count | Self Size | Retained Size |\n| ---: | ----------- | ----: | --------: | ------------: |\n|    1 | `Function`  |   568 |   18.7 KB |        5.4 MB |\n|    2 | `Structure` |   247 |   27.0 KB |        2.0 MB |\n```\n\nThe markdown format includes searchable object listings, retainer chains showing how objects are kept alive, and quick grep commands for finding memory issues:\n\n```\ngrep 'type=Function' profile.md      # Find all Function objects\ngrep 'size=[0-9]\\{5,\\}' profile.md   # Find objects >= 10KB\ngrep 'gcroot=1' profile.md           # Find all GC roots\n```\n\n[Native JSON5 Support](#native-json5-support)\n\nBun now includes a built-in JSON5 parser with `Bun.JSON5.parse()`\n\nand `Bun.JSON5.stringify()`\n\n, plus native `.json5`\n\nfile imports.\n\n[JSON5](https://json5.org/) is a superset of JSON that adds developer-friendly features like comments, trailing commas, unquoted keys, single-quoted strings, and hexadecimal numbers. It's used by major projects including Chromium, Next.js, Babel, and WebStorm.\n\n``` js\n// Parse JSON5 strings\nconst config = Bun.JSON5.parse(`{\n  // Database configuration\n  host: 'localhost',\n  port: 5432,\n  ssl: true,\n}`);\n\n// Stringify objects to JSON5\nconst output = Bun.JSON5.stringify({ name: \"app\", version: 1 });\n\n// Import .json5 files directly\nimport settings from \"./config.json5\";\n```\n\nJSON5 is particularly useful for configuration files where comments and trailing commas improve readability and maintainability.\n\n`Bun.JSONL`\n\nfor Streaming JSONL Parsing\n\n`Bun.JSONL`\n\nfor Streaming JSONL ParsingBun now has built-in support for parsing [JSONL](https://jsonlines.org/) (newline-delimited JSON). The parser is implemented in C++ using JavaScriptCore's optimized JSON parser, providing fast parsing for both complete inputs and streaming use cases.\n\n`Bun.JSONL.parse()`\n\n`Bun.JSONL.parse()`\n\nParse a complete JSONL string or `Uint8Array`\n\nand return an array of all parsed values:\n\n``` js\nconst results = Bun.JSONL.parse('{\"name\":\"Alice\"}\\n{\"name\":\"Bob\"}\\n');\n// [{ name: \"Alice\" }, { name: \"Bob\" }]\n\n// Also works with Uint8Array (UTF-8 BOM automatically skipped)\nconst buffer = new TextEncoder().encode('{\"a\":1}\\n{\"b\":2}\\n');\nconst records = Bun.JSONL.parse(buffer);\n// [{ a: 1 }, { b: 2 }]\n```\n\n`Bun.JSONL.parseChunk()`\n\n`Bun.JSONL.parseChunk()`\n\nFor streaming scenarios, `parseChunk`\n\nparses as many complete values as possible and returns how far it got—useful when receiving data incrementally from a network stream:\n\n``` js\nconst chunk = '{\"id\":1}\\n{\"id\":2}\\n{\"id\":3';\n\nconst result = Bun.JSONL.parseChunk(chunk);\nresult.values; // [{ id: 1 }, { id: 2 }]\nresult.read; // 17 — characters consumed\nresult.done; // false — incomplete value remains\nresult.error; // null — no parse error\n```\n\nUse `read`\n\nto slice off consumed input and carry forward the remainder:\n\n``` js\nlet buffer = \"\";\n\nfor await (const chunk of stream) {\n  buffer += chunk;\n  const result = Bun.JSONL.parseChunk(buffer);\n\n  for (const value of result.values) {\n    handleRecord(value);\n  }\n\n  // Keep only the unconsumed portion\n  buffer = buffer.slice(result.read);\n}\n```\n\n[S3 ](#s3-presign-now-supports-contentdisposition-and-type-options)`presign()`\n\nnow supports `contentDisposition`\n\nand `type`\n\noptions\n\n`presign()`\n\nnow supports `contentDisposition`\n\nand `type`\n\noptionsFixed an issue where `S3File.presign()`\n\nwas ignoring the `contentDisposition`\n\nand `type`\n\noptions when generating presigned URLs. These options are now properly included as `response-content-disposition`\n\nand `response-content-type`\n\nquery parameters.\n\nThis is particularly useful when you want browsers to download files as attachments instead of displaying them inline:\n\n``` js\nimport { S3Client } from \"bun\";\n\nconst s3 = new S3Client({\n  region: \"us-east-1\",\n  endpoint: \"https://s3.us-east-1.amazonaws.com\",\n  accessKeyId: process.env.AWS_ACCESS_KEY_ID,\n  secretAccessKey: process.env.AWS_SECRET_ACCESS_KEY,\n  bucket: \"my-bucket\",\n});\n\nconst file = s3.file(\"report.pdf\");\n\nconst url = file.presign({\n  method: \"GET\",\n  expiresIn: 900,\n  contentDisposition: 'attachment; filename=\"quarterly-report.pdf\"',\n  type: \"application/octet-stream\",\n});\n// URL now includes response-content-disposition and response-content-type parameters\n```\n\n`bun pm pack`\n\nnow respects changes to `package.json`\n\nfrom lifecycle scripts\n\n`bun pm pack`\n\nnow respects changes to `package.json`\n\nfrom lifecycle scripts`bun pm pack`\n\nnow re-reads `package.json`\n\nafter running `prepack`\n\n, `prepare`\n\n, and `prepublishOnly`\n\nscripts, ensuring any modifications made by these scripts are included in the tarball.\n\nThis matches npm's behavior and enables compatibility with tools like [clean-package](https://github.com/roydukkey/clean-package) that modify `package.json`\n\nduring the pack process.\n\n```\n// package.json\n{\n  \"name\": \"my-package\",\n  \"version\": \"1.0.0\",\n  \"scripts\": {\n    \"prepack\": \"node prepack.js\"\n  },\n  \"description\": \"Original description\",\n  \"devDependencies\": { /* ... */ }\n}\n\n// prepack.js - removes devDependencies before packing\nconst fs = require('fs');\nconst pkg = JSON.parse(fs.readFileSync('package.json', 'utf8'));\ndelete pkg.devDependencies;\npkg.description = 'Production build';\nfs.writeFileSync('package.json', JSON.stringify(pkg, null, 2));\n```\n\nPreviously, the tarball would contain the original `package.json`\n\n. Now it correctly contains the modified version.\n\n`node:inspector`\n\nProfiler API\n\n`node:inspector`\n\nProfiler APIBun now implements the `node:inspector`\n\nProfiler API for CPU profiling via the Chrome DevTools Protocol.\n\n**Supported methods:**\n\n`Profiler.enable`\n\n/`Profiler.disable`\n\n`Profiler.start`\n\n/`Profiler.stop`\n\n`Profiler.setSamplingInterval`\n\nBoth callback (`node:inspector`\n\n) and promise (`node:inspector/promises`\n\n) APIs are supported.\n\n``` python\nimport inspector from \"node:inspector/promises\";\n\nconst session = new inspector.Session();\nsession.connect();\n\nawait session.post(\"Profiler.enable\");\nawait session.post(\"Profiler.start\");\n\n// ... code to profile ...\n\nconst { profile } = await session.post(\"Profiler.stop\");\nawait session.post(\"Profiler.disable\");\n// profile is in Chrome DevTools Protocol format\n```\n\n- Fixed:\n`Bun.profile()`\n\nfrom`bun:jsc`\n\nreturning empty traces on subsequent calls\n\n[Faster ](#faster-buffer-swap16-and-buffer-swap64)`Buffer.swap16()`\n\nand `Buffer.swap64()`\n\n`Buffer.swap16()`\n\nand `Buffer.swap64()`\n\n`Buffer.swap16()`\n\nis now **1.8x faster** and `Buffer.swap64()`\n\nis now **3.6x faster** by using optimized CPU intrinsics instead of byte-by-byte swapping loops.\n\n``` js\nconst buf = Buffer.alloc(64 * 1024);\n\n// Swap byte pairs in-place (e.g., for UTF-16 encoding conversion)\nbuf.swap16();\n\n// Swap 8-byte chunks in-place (e.g., for 64-bit integer endianness)\nbuf.swap64();\n```\n\n| Operation | Before | After | Improvement |\n|---|---|---|---|\n| swap16 | 1.00 µs | 0.56 µs | 1.8x faster |\n| swap64 | 2.02 µs | 0.56 µs | 3.6x faster |\n\nBun now matches or exceeds Node.js performance for all buffer swap operations.\n\n[Fixed: Bun.stringWidth - grapheme breaking with GB9c Support](#fixed-bun-stringwidth-grapheme-breaking-with-gb9c-support)\n\nBun's grapheme breaking implementation has been upgraded to properly support Unicode's GB9c rule for Indic Conjunct Break. This means Devanagari and other Indic script conjuncts now correctly form single grapheme clusters.\n\nPreviously, Indic conjunct sequences (consonant + virama + consonant) were incorrectly split into multiple grapheme clusters. Now `Bun.stringWidth()`\n\nand other string operations handle these scripts correctly:\n\n```\n// Devanagari conjuncts now correctly treated as single grapheme clusters\nBun.stringWidth(\"क्ष\"); // Ka+Virama+Ssa → width 2 (single cluster)\nBun.stringWidth(\"क्‍ष\"); // Ka+Virama+ZWJ+Ssa → width 2 (single cluster)\nBun.stringWidth(\"क्क्क\"); // Ka+Virama+Ka+Virama+Ka → width 3 (single cluster)\n```\n\nThis update also reduces the internal table size from ~70KB to ~51KB while adding more comprehensive Unicode support.\n\n[Next.js 16 Cache Components compatibility](#next-js-16-cache-components-compatibility)\n\nAdded the `_idleStart`\n\nproperty to `Timeout`\n\nobjects returned by `setTimeout()`\n\nand `setInterval()`\n\n, matching Node.js behavior. This property returns a monotonic timestamp (in milliseconds) representing when the timer was created or last rescheduled.\n\nThis fixes compatibility with Next.js 16's Cache Components feature, which relies on this internal property to coordinate timers.\n\n``` js\nconst timer = setTimeout(() => {}, 1000);\nconsole.log(timer._idleStart); // monotonic timestamp in ms\nclearTimeout(timer);\n```\n\n`replMode`\n\noption for `Bun.Transpiler`\n\n`replMode`\n\noption for `Bun.Transpiler`\n\nA new `replMode`\n\noption for `Bun.Transpiler`\n\ntransforms code for interactive REPL evaluation. This enables building a Node.js-compatible REPL using `Bun.Transpiler`\n\nwith `vm.runInContext`\n\nfor persistent variable scope.\n\nKey features:\n\n**Variable hoisting**:`var`\n\n/`let`\n\n/`const`\n\ndeclarations are hoisted outside the IIFE wrapper for persistence across REPL lines: Allows re-declaration in subsequent REPL inputs`const`\n\n→`let`\n\nconversion**Expression result capture**: Wraps the last expression for easy result extraction** Object literal detection**: Auto-detects`{a: 1}`\n\nas an object literal instead of a block statement**Top-level await support**: Automatically uses async IIFE wrappers when needed\n\n``` python\nimport vm from \"node:vm\";\n\nconst transpiler = new Bun.Transpiler({\n  loader: \"tsx\",\n  replMode: true,\n});\n\nconst context = vm.createContext({ console, Promise });\n\nasync function repl(code: string) {\n  const transformed = transpiler.transformSync(code);\n  const result = await vm.runInContext(transformed, context);\n  return result.value;\n}\n\n// Variables persist across REPL lines\nawait repl(\"var x = 10\"); // 10\nawait repl(\"x + 5\"); // 15\n\n// Classes and functions are hoisted to the context\nawait repl(\"class Counter {}\"); // [class Counter]\nawait repl(\"new Counter()\"); // Counter {}\n\n// Object literals are auto-detected\nawait repl(\"{a: 1, b: 2}\"); // {a: 1, b: 2}\n\n// Top-level await works\nawait repl(\"await Promise.resolve(42)\"); // 42\n```\n\n[Increased Maximum HTTP Header Count](#increased-maximum-http-header-count)\n\nThe maximum number of HTTP headers allowed in requests and responses has been doubled from 100 to 200. This improves compatibility with services that send many headers, such as APIs with extensive metadata or proxies that append multiple forwarding headers.\n\n[WebSocket URL Credentials Support](#websocket-url-credentials-support)\n\nWebSocket connections now properly forward credentials embedded in URLs as Basic Authorization headers, matching Node.js behavior.\n\nWhen connecting to a WebSocket URL with embedded credentials like `ws://user:pass@host`\n\n, Bun now automatically extracts the credentials and sends them as a properly encoded `Authorization: Basic`\n\nheader during the WebSocket upgrade handshake.\n\n``` js\n// Credentials are now automatically forwarded\nconst ws = new WebSocket(\"ws://username:password@example.com/socket\");\n\n// User-provided Authorization headers take precedence\nconst ws2 = new WebSocket(\"ws://user:pass@example.com/socket\", {\n  headers: {\n    Authorization: \"Bearer custom-token\", // This will be used instead\n  },\n});\n```\n\nThis fixes compatibility with services like Puppeteer connecting to remote browser instances (e.g., Bright Data's scraping browser) that require URL-based authentication.\n\n[Faster JavaScript Built-ins](#faster-javascript-built-ins)\n\nBun v1.3.7 upgrades WebKit, bringing significant performance improvements to several JavaScript built-in methods:\n\n**String methods:**\n\n`String.prototype.isWellFormed`\n\nand`String.prototype.toWellFormed`\n\nare**5.2-5.4x faster** using simdutf\n\n**RegExp methods:**\n\n`RegExp.prototype[Symbol.matchAll]`\n\nand`RegExp.prototype[Symbol.replace]`\n\nreimplemented in C++\n\n[S3 ](#s3-contentencoding-option)`contentEncoding`\n\nOption\n\n`contentEncoding`\n\nOptionBun's S3 client now supports setting the `Content-Encoding`\n\nheader when uploading objects via `.write()`\n\nand `.writer()`\n\nmethods.\n\nThis is useful when uploading pre-compressed content to S3, allowing you to specify encodings like `gzip`\n\n, `br`\n\n(Brotli), or `deflate`\n\n:\n\n``` js\nimport { s3 } from \"bun\";\n\nconst file = s3.file(\"my-bucket/data.json.gz\");\n\n// With .write()\nawait file.write(compressedData, { contentEncoding: \"gzip\" });\n\n// With .writer()\nconst writer = file.writer({ contentEncoding: \"gzip\" });\nwriter.write(compressedData);\nawait writer.end();\n\n// With bucket.write()\nconst bucket = s3.bucket(\"my-bucket\");\nawait bucket.write(\"data.json.br\", brotliData, { contentEncoding: \"br\" });\n```\n\n`bun:ffi`\n\nnow respects `C_INCLUDE_PATH`\n\nand `LIBRARY_PATH`\n\nenvironment variables\n\n`bun:ffi`\n\nnow respects `C_INCLUDE_PATH`\n\nand `LIBRARY_PATH`\n\nenvironment variablesBun's built-in C compiler (`bun:ffi`\n\n) now respects the standard `C_INCLUDE_PATH`\n\nand `LIBRARY_PATH`\n\nenvironment variables. This fixes compilation on NixOS and other systems that don't use standard FHS paths like `/usr/include`\n\nor `/usr/lib`\n\n.\n\n``` js\nimport { cc } from \"bun:ffi\";\n\nconst {\n  symbols: { hello },\n} = cc({\n  source: \"./hello.c\",\n  symbols: {\n    hello: {\n      returns: \"int\",\n    },\n  },\n});\n\n// On NixOS, set C_INCLUDE_PATH and LIBRARY_PATH to point to your Nix store paths\n// C_INCLUDE_PATH=/nix/store/.../include LIBRARY_PATH=/nix/store/.../lib bun run hello.js\n```\n\n[Dependency updates](#dependency-updates)\n\n- Bun now uses Mimalloc v3 for the natively-managed memory heap. This reduces memory usage in multi-threaded scenarios. Please let us know if you run into any increases in memory usage.\n- LOLHTML updated to v2.7.1\n- TinyCC has been updated to the latest version, and we've implemented Windows ARM64 support.\n- BoringSSL has been updated.\n\n[Bugfixes](#bugfixes)\n\n[Bundler bugfixes](#bundler-bugfixes)\n\n- Fixed: CSS logical border-radius properties (\n`border-start-start-radius`\n\n,`border-start-end-radius`\n\n,`border-end-end-radius`\n\n,`border-end-start-radius`\n\n) being silently dropped by the CSS bundler. - Fixed: Bundler producing invalid JavaScript when minifying files with both default and named imports from the\n`\"bun\"`\n\nmodule (e.g.,`import bun, { embeddedFiles } from \"bun\"`\n\n) due to missing semicolons between statements - Fixed: a panic in the bundler when using code splitting on Windows\n- Fixed: Bundler's\n`module.exports = require()`\n\nredirect optimization being disabled when legal comments (`/*! ... */`\n\n) were present in wrapper modules like Express's`index.js`\n\n, resulting in unnecessary wrapper functions in the output - Fixed: Crash in\n`bun build`\n\nwhen using macros - Fixed:\n`Bun.build`\n\nhanging indefinitely when called from within a macro during bundling—now throws a clear error explaining the deadlock and suggesting`Bun.spawnSync`\n\nas a workaround. - Fixed:\n`reactFastRefresh`\n\nin`bun.build`\n\nnow works with non-browser targets - Fixed: Bundler producing duplicate export statements when one entry point re-exports from another entry point with code splitting enabled.\n- Fixed: Bundler generating invalid import paths (missing\n`./`\n\nprefix) when a file imports from the same directory in code-split builds. - Fixed: Named Function Expressions Shadowing Outer Symbols\n\n`bun build --compile`\n\n`bun build --compile`\n\n- Fixed: Compiled binaries with\n`autoloadBunfig: false`\n\nincorrectly loading`bunfig.toml`\n\nwhen`execArgv`\n\nwas also provided - Fixed: Native module export corruption when using\n`bun build --compile`\n\nwith multiple NAPI modules on Linux, where the second module would incorrectly receive the first module's exports - Fixed: Standalone executables compiled with\n`--compile-exec-argv`\n\nincorrectly intercepting`--version`\n\n,`-v`\n\n,`--help`\n\n, and`-h`\n\nflags before user code could handle them, breaking CLI applications using libraries like Commander.js that define their own version and help commands - Fixed: Lazy-loaded chunks from dynamic imports not appearing in\n`frontend.files`\n\nwhen using`--splitting`\n\nwith`--compile`\n\nin fullstack builds - Fixed:\n`BUN_OPTIONS`\n\nenvironment variable not being applied as runtime options for standalone executables created with`bun build --compile`\n\n, which caused options like`--bun`\n\nto incorrectly appear in`process.argv`\n\ninstead of being parsed as Bun runtime options. - Fixed: Incorrect offset calculations in single-file executables on non-ARM64 macOS platforms when codesigning was not enabled\n- Fixed a crash when running standalone executables with bytecode cache on Windows caused by incorrect bytecode alignment in PE sections.\n\n`bun install`\n\n`bun install`\n\n- Fixed:\n`bun update --interactive`\n\nnot selecting packages when pressing 'l' to toggle between Target and Latest versions, causing the underline indicator to disappear and packages to be excluded when confirming - Fixed:\n`bun install --yarn`\n\ngenerating invalid`yarn.lock`\n\nfiles when using`workspace:*`\n\ndependencies in monorepos - Fixed:\n`bun install --frozen-lockfile`\n\nincorrectly using the default npm registry instead of scope-specific registries configured in`bunfig.toml`\n\nwhen the lockfile had an empty registry URL for scoped packages (e.g.,`@orgname/package`\n\n). - Fixed:\n`bun install`\n\nnow shows the dependency name in error messages when a`file:`\n\npath resolution fails due to a stale lockfile, instead of the misleading \"Bun could not find a package.json file to install from\" error. - Fixed:\n`bun add`\n\ncrashing with \"panic: Assertion failure: Expected metadata to be set\" when HTTP requests fail before receiving response headers (e.g., network connection refused, firewall blocking requests, or timeouts)\n\n`bun test`\n\n`bun test`\n\n- Fixed:\n`bun test --inspect`\n\nnow properly sends`TestReporter.found`\n\n,`TestReporter.start`\n\n, and`TestReporter.end`\n\nevents to debugger clients that connect after test discovery has begun, enabling IDE integrations and debugging tools to receive real-time test execution telemetry without requiring`--inspect-wait`\n\n. - Fixed:\n`assert.partialDeepStrictEqual`\n\nincorrectly requiring exact equality for Map objects instead of checking if the expected Map is a subset of the actual Map - Fixed:\n`jest.useRealTimers()`\n\nnot properly removing the`setTimeout.clock`\n\nproperty, which broke React Testing Library and other libraries that detect fake timers using`hasOwnProperty`\n\nchecks\n\n`Bun.serve()`\n\n`Bun.serve()`\n\n- Fixed: Exporting a\n`Server`\n\ninstance from`Bun.serve()`\n\nas the default export no longer causes a \"Maximum call stack\" error. Bun's entry point wrapper previously detected the`fetch`\n\nmethod on the running server and incorrectly tried to call`Bun.serve()`\n\non it again. - Fixed: Scripts that export\n`globalThis`\n\n(e.g.,`module.exports = globalThis`\n\nor`export default globalThis`\n\n) no longer incorrectly trigger Bun's auto-serve detection and start a development server on port 3000 - Fixed:\n`--no-clear-screen`\n\nflag and`BUN_CONFIG_NO_CLEAR_TERMINAL_ON_RELOAD`\n\nenvironment variable not being respected during HMR reloads when using`Bun.serve`\n\nwith`hmr: true`\n\n[Bun Shell](#bun-shell)\n\n- Fixed:\n`ls -l`\n\nin Bun's shell now correctly displays long listing format with file type, permissions, hard link count, UID, GID, size, modification time, and filename instead of showing the same output as`ls`\n\nwithout flags - Fixed: Crash in shell interpreter when an error occurred during initialization in certain cases\n- Fixed:\n`$`\n\n...`.cwd(\".\")`\n\n,`.cwd(\"\")`\n\n, and`.cwd(\"./\")`\n\nin Bun shell causing ENOENT errors with paths ending in \"undefined\" when used in loops\n\n[Bun APIs](#bun-apis)\n\n- Fixed: Added missing stack overflow checks in\n`Bun.JSONC.parse`\n\nand`Bun.TOML.parse`\n\n`node:http2`\n\n`node:http2`\n\n- Fixed: HTTP/2 streams sending an extra empty DATA frame when using\n`req.write(data)`\n\nfollowed by`req.end()`\n\n, which caused AWS ALB and other strict HTTP/2 servers to reject connections with`NGHTTP2_FRAME_SIZE_ERROR`\n\n- Fixed: initial stream window size to use\n`DEFAULT_WINDOW_SIZE`\n\nuntil`SETTINGS_ACK`\n\nis received per RFC 7540 Section 6.5.1 - Fixed: HTTP/2 streams failing with\n`NGHTTP2_PROTOCOL_ERROR`\n\nwhen connecting to Fauna - Fixed: gRPC requests failing with\n`NGHTTP2_FRAME_SIZE_ERROR`\n\nwhen servers advertise non-default`maxFrameSize`\n\nsettings (regression since v1.2.16) - Fixed: Settings validation using incorrect integer conversion that truncated large values\n- Improved: properly adjusts existing stream windows when\n`INITIAL_WINDOW_SIZE`\n\nsetting changes - Improved: implements\n`maxHeaderListSize`\n\nchecking per RFC 7540 Section 6.5.2 - Improved: tracks cumulative header list size using HPACK entry overhead\n- Improved; adds validation for\n`customSettings`\n\noption (up to 10 custom settings, matching Node.js) - Improved: validates setting IDs and values per RFC 7540 specifications\n\n[Fetch API](#fetch-api)\n\n- Fixed: Hypothetical crash when using HTTP proxy with redirects if the socket closes during redirect processing\n- Fixed:\n`fetch()`\n\nmTLS incorrectly used the first client certificate for subsequent keepalive requests to the same host, ignoring per-request`tls`\n\noptions - Fixed:\n`Request.prototype.text()`\n\nincorrectly throwing \"TypeError: undefined is not a function\" in certain cases under load - Fixed:\n`Request`\n\nconstructor ignoring`cache`\n\nand`mode`\n\noptions - Fixed:\n`NO_PROXY`\n\nenvironment variable not respecting port numbers (e.g.,`NO_PROXY=localhost:8080`\n\nwould incorrectly bypass the proxy for all requests to`localhost`\n\nregardless of port)\n\n`node:fs`\n\n`node:fs`\n\n- Fixed:\n`realpathSync`\n\nblocking indefinitely when called on a FIFO (named pipe) on POSIX systems - Fixed:\n`Bun.Glob`\n\nand`fs.readdirSync`\n\nwith`recursive: true`\n\nfailing to find files on bind-mounted filesystems, FUSE, NFS, and some ext4 configurations in Docker environments - Fixed:\n`fs.Dirent.isFIFO()`\n\nincorrectly returning`true`\n\nfor files on sshfs, NFS, and other remote filesystems that don't populate`d_type`\n\n- Fixed:\n`fs.watch`\n\non directories not emitting`change`\n\nevents for file modifications on Linux. Previously, when watching a directory, files created after the watch was established would only emit a`rename`\n\nevent on creation, but subsequent modifications would not emit`change`\n\nevents.\n\n`node:https`\n\n& TLS\n\n`node:https`\n\n& TLS- Fixed: TLS options (\n`ca`\n\n,`cert`\n\n,`key`\n\n,`passphrase`\n\n,`ciphers`\n\n,`servername`\n\n,`secureOptions`\n\n,`rejectUnauthorized`\n\n) from`agent.options`\n\nand`agent.connectOpts`\n\nnot being respected in the`https`\n\nmodule, improving compatibility with libraries like`https-proxy-agent`\n\n- Fixed: race condition where\n`request.socket._secureEstablished`\n\ncould return`false`\n\nin HTTPS request handlers even after the TLS handshake had completed - Fixed: TLS v1.2 renegotation\n`rejectUnauthorized`\n\noption being incorrectly ignored in TLS socket`setVerifyMode`\n\n, which could cause certificate verification to behave unexpectedly during TLS renegotiation.\n\n`node:http`\n\n`node:http`\n\n- Request bodies in GET requests are now supported.\n- Fixed: Multipart uploads with\n`form-data`\n\n+`node-fetch@2`\n\n+`fs.createReadStream()`\n\nbeing truncated\n\n[WebSocket (](#websocket-ws)`ws`\n\n)\n\n`ws`\n\n)- Fixed:\n`handleProtocols`\n\noption in`ws`\n\nWebSocketServer not correctly setting the selected protocol in WebSocket upgrade responses - Fixed:\n`ws.once()`\n\nonly working on the first call for each event type in the`ws`\n\npackage\n\n[Node-API (NAPI)](#node-api-napi)\n\n- Fixed: crash in Node-API that caused corrupted data when using native modules like\n`impit`\n\n. The first issue occurred when property name strings were freed by the caller but Bun retained dangling pointers in the atom string table. The second issue occurred when extracting`.buffer`\n\nfrom an external buffer would prematurely free the backing data when the original Buffer was garbage collected.\n\n[Streams](#streams)\n\n- Fixed:\n`ReadableStreamDefaultController.desiredSize`\n\nthrowing`TypeError: null is not an object`\n\ninstead of returning`null`\n\nwhen accessing it after the stream has been detached during cleanup (e.g., when piping a`ReadableStream`\n\nbody to`fetch`\n\nand the downstream closes unexpectedly)\n\n`bun:sql`\n\n(MySQL)\n\n`bun:sql`\n\n(MySQL)- Fixed: MySQL transactions hanging when executing sequential transactions in a loop where an\n`INSERT`\n\nis awaited inside the transaction callback and a`SELECT`\n\nquery is returned as an array without being awaited - Fixed: MySQL VARCHAR/CHAR/TEXT columns with binary collations (like\n`utf8mb4_bin`\n\n) incorrectly returning`Buffer`\n\ninstead of`string`\n\n`Bun.Terminal`\n\n`Bun.Terminal`\n\n- Fixed:\n`Bun.Terminal`\n\ncallbacks (`data`\n\n,`exit`\n\n,`drain`\n\n) not being invoked when the terminal was created inside`AsyncLocalStorage.run()`\n\n[Memory Management](#memory-management)\n\n- Fixed: Memory leak in YAML parser\n- Fixed: Memory leak when sockets are reused for reconnection (common with MongoDB driver-like usage)\n\n[CLI & Tooling](#cli-tooling)\n\n- Fixed:\n`bun completions`\n\ncrashing with`BrokenPipe`\n\nerror when piped to commands that close stdout early (e.g.,`bun completions | true`\n\n) - Fixed: Fish shell autocompletion not working for\n`bun update`\n\ncommand and its flags (like`--global`\n\n,`--dry-run`\n\n,`--force`\n\n) - Fixed:\n`bun init --minimal`\n\nincorrectly creating Cursor rules files and`CLAUDE.md`\n\nwhen the`--minimal`\n\nflag should only create`package.json`\n\nand`tsconfig.json`\n\n- Fixed:\n`bun <file>`\n\non unsupported file types (`.css`\n\n,`.html`\n\n,`.yaml`\n\n, etc.) now shows \"Cannot run\" with the file type instead of the misleading \"File not found\" error - Fixed:\n`bun`\n\nnpm package now shows a helpful error message when postinstall script hasn't run, instead of silently exiting with code 0. This helps diagnose issues when installing with`--ignore-scripts`\n\nor using pnpm (which skips postinstall scripts by default). - Fixed:\n`BUN_OPTIONS`\n\nenvironment variable incorrectly parsing bare flags (flags without`=`\n\n) when followed by other flags, causing options like`--cpu-prof`\n\nto be ignored when specified as`BUN_OPTIONS=\"--cpu-prof --cpu-prof-dir=profiles\"`\n\n[TypeScript Definitions](#typescript-definitions)\n\n- Fixed: Renamed\n`Bun.Build.Target`\n\ntype to`Bun.Build.CompileTarget`\n\nin TypeScript definitions to avoid confusion with the existing`target`\n\noption in`Bun.build()`\n\n- Fixed: TypeScript errors in the\n`react-tailwind`\n\ntemplate's`build.ts`\n\nwhen using strict type checking\n\n[Node.js Compatibility](#node-js-compatibility)\n\n- Fixed: Properly handle errors when strings exceed the ~4GB maximum length limit, now correctly throwing\n`ERR_STRING_TOO_LONG`\n\n, fixing a SIGILL crash impacting some Claude Code users - Fixed:\n`process.stdout.write()`\n\nnot emitting EPIPE errors on broken pipes, causing processes to exit with code 0 instead of 1 when stdout is destroyed - Fixed:\n`TypeError: this._refreshLine is not a function`\n\nwhen using tab completion with`node:readline/promises`\n\n- Improved:\n`node:util`\n\nnow uses`Bun.stringWidth`\n\ndirectly, offering improved performance.\n\n[Windows](#windows)\n\n- Fixed: panic when reading or writing large files (>4GB) on Windows due to integer overflow in libuv buffer size parameters\n\n[Build System](#build-system)\n\n- Fixed: NixOS debug builds failing with\n`_FORTIFY_SOURCE requires compiling with optimization`\n\nerror", "url": "https://wpnews.pro/news/bun-v1-3-7", "canonical_source": "https://bun.com/blog/bun-v1.3.7", "published_at": "2026-01-27 06:30:58+00:00", "updated_at": "2026-05-22 20:41:29.253276+00:00", "lang": "en", "topics": ["developer-tools", "open-source"], "entities": ["Bun", "JavaScriptCore", "WebKit", "Safari"], "alternates": {"html": "https://wpnews.pro/news/bun-v1-3-7", "markdown": "https://wpnews.pro/news/bun-v1-3-7.md", "text": "https://wpnews.pro/news/bun-v1-3-7.txt", "jsonld": "https://wpnews.pro/news/bun-v1-3-7.jsonld"}}