温馨提示:本站仅提供公开网络链接索引服务,不存储、不篡改任何第三方内容,所有内容版权归原作者所有
AI智能索引来源:http://www.bun.com/docs/bundler
点击访问原文链接
Bundler - BunSkip to main contentBun home pageSearch...⌘KInstall BunSearch...NavigationCoreBundlerRuntimePackage ManagerBundlerTest RunnerGuidesReferenceBlogFeedbackdiv:first-child]:!hidden peer-[.is-custom]:[&>div:first-child]:sm:!hidden peer-[.is-custom]:[&>div:first-child]:md:!hidden peer-[.is-custom]:[&>div:first-child]:lg:!hidden peer-[.is-custom]:[&>div:first-child]:xl:!hidden">CoreBundlerDevelopment ServerFullstack dev serverHot reloadingAsset ProcessingHTML & static sitesStandalone HTMLCSSLoadersSingle File ExecutableSingle-file executableExtensionsPluginsMacrosOptimizationBytecode CachingMinifierMigrationesbuildOn this pageAt a GlanceWhy bundle?Basic exampleWatch modeContent typesAssetsPluginsAPIentrypointsfilesBundle entirely from memoryOverride files on diskMix disk and virtual filesoutdirtargetformatformat: “esm” - ES Moduleformat: “cjs” - CommonJSformat: “iife” - IIFEjsxsplittingpluginsenvenv: “inline”env: “PUBLIC_*” (prefix)env: “disable”sourcemapminifyexternalpackagesnamingrootpublicPathdefineloaderbannerfooterdropfeaturesoptimizeImportsmetafileMarkdown metafilemetafile option formatsOutputsBytecodeExecutablesLogs and errorsReferenceCLI UsageGeneral ConfigurationOutput & File HandlingFile NamingBundling OptionsMinification & OptimizationDevelopment FeaturesStandalone ExecutablesWindows Executable DetailsExperimental & App BuildingCoreBundlerCopy pagespan]:line-clamp-1 overflow-hidden group flex items-center py-0.5 gap-1 text-sm text-gray-950/50 dark:text-white/50 group-hover:text-gray-950/70 dark:group-hover:text-white/70 rounded-none rounded-r-xl border px-3 border-gray-200 aspect-square dark:border-white/[0.07] bg-background-light dark:bg-background-dark hover:bg-gray-600/5 dark:hover:bg-gray-200/5" aria-label="More actions" type="button" id="radix-_R_2shjinpfd9rqaabsnpfdb_" aria-haspopup="menu" aria-expanded="false" data-state="closed">*]:[overflow-wrap:anywhere]">Bun’s fast native bundler for JavaScript, TypeScript, JSX, and more

Copy pagespan]:line-clamp-1 overflow-hidden group flex items-center py-0.5 gap-1 text-sm text-gray-950/50 dark:text-white/50 group-hover:text-gray-950/70 dark:group-hover:text-white/70 rounded-none rounded-r-xl border px-3 border-gray-200 aspect-square dark:border-white/[0.07] bg-background-light dark:bg-background-dark hover:bg-gray-600/5 dark:hover:bg-gray-200/5" aria-label="More actions" type="button" id="radix-_R_5hjinpfd9rqaabsnpfdb_" aria-haspopup="menu" aria-expanded="false" data-state="closed">Bun’s fast native bundler can be used via the bun build CLI command or the Bun.build() JavaScript API. ​At a Glance JS API: await Bun.build({ entrypoints, outdir }) CLI: bun build --outdir ./out Watch: --watch for incremental rebuilds Targets: --target browser|bun|node Formats: --format esm|cjs|iife (experimental for cjs/iife) JavaScript CLIbuild.tsCopyawait Bun.build({ entrypoints: ['./index.tsx'], outdir: './build', }); terminalCopybun build ./index.tsx --outdir ./build It’s fast. The numbers below represent performance on esbuild’s three.js benchmark. ​Why bundle? The bundler is a key piece of infrastructure in the JavaScript ecosystem. As a brief overview of why bundling is so important: Reducing HTTP requests. A single package in node_modules may consist of hundreds of files, and large applications may have dozens of such dependencies. Loading each of these files with a separate HTTP request becomes untenable very quickly, so bundlers are used to convert our application source code into a smaller number of self-contained “bundles” that can be loaded with a single request. Code transforms. Modern apps are commonly built with languages or tools like TypeScript, JSX, and CSS modules, all of which must be converted into plain JavaScript and CSS before they can be consumed by a browser. The bundler is the natural place to configure these transformations. Framework features. Frameworks rely on bundler plugins & code transformations to implement common patterns like file-system routing, client-server code co-location (think getServerSideProps or Remix loaders), and server components. Full-stack Applications. Bun’s bundler can handle both server and client code in a single command, enabling optimized production builds and single-file executables. With build-time HTML imports, you can bundle your entire application — frontend assets and backend server — into a single deployable unit. Let’s jump into the bundler API. The Bun bundler is not intended to replace tsc for typechecking or generating type declarations. ​Basic example Let’s build our first bundle. You have the following two files, which implement a simple client-side rendered React app. index.tsxComponent.tsxCopyimport * as ReactDOM from "react-dom/client"; import { Component } from "./Component"; const root = ReactDOM.createRoot(document.getElementById("root")!); root.render(Component message="Sup!" />); Here, index.tsx is the “entrypoint” to our application. Commonly, this will be a script that performs some side effect, like starting a server or—in this case—initializing a React root. Because we’re using TypeScript & JSX, we need to bundle our code before it can be sent to the browser. To create our bundle: build.tsterminalCopyawait Bun.build({ entrypoints: ["./index.tsx"], outdir: "./out", }); For each file specified in entrypoints, Bun will generate a new bundle. This bundle will be written to disk in the ./out directory (as resolved from the current working directory). After running the build, the file system looks like this: file systemCopy. ├── index.tsx ├── Component.tsx └── out └── index.js The contents of out/index.js will look something like this: out/index.jsCopy// out/index.js // ... // ~20k lines of code // including the contents of `react-dom/client` and all its dependencies // this is where the $jsxDEV and $createRoot functions are defined // Component.tsx function Component(props) { return $jsxDEV( "p", { children: props.message, }, undefined, false, undefined, this, ); } // index.tsx var rootNode = document.getElementById("root"); var root = $createRoot(rootNode); root.render( $jsxDEV( Component, { message: "Sup!", }, undefined, false, undefined, this, ), ); ​Watch mode Like the runtime and test runner, the bundler supports watch mode natively. terminalCopybun build ./index.tsx --outdir ./out --watch ​Content types Like the Bun runtime, the bundler supports an array of file types out of the box. The following table breaks down the bundler’s set of standard “loaders”. Refer to Bundler > File types for full documentation. ExtensionsDetails.js .jsx .cjs .mjs .mts .cts .ts .tsxUses Bun’s built-in transpiler to parse the file and transpile TypeScript/JSX syntax to vanilla JavaScript. The bundler executes a set of default transforms including dead code elimination and tree shaking. At the moment Bun does not attempt to down-convert syntax; if you use recently ECMAScript syntax, that will be reflected in the bundled code..jsonJSON files are parsed and inlined into the bundle as a JavaScript object.

js
import pkg from "./package.json";
pkg.name; // => "my-package"
.jsoncJSON with comments. Files are parsed and inlined into the bundle as a JavaScript object.

js
import config from "./config.jsonc";
config.name; // => "my-config"
.tomlTOML files are parsed and inlined into the bundle as a JavaScript object.

js
import config from "./bunfig.toml";
config.logLevel; // => "debug"
.yaml .ymlYAML files are parsed and inlined into the bundle as a JavaScript object.

js
import config from "./config.yaml";
config.name; // => "my-app"
.txtThe contents of the text file are read and inlined into the bundle as a string.

js
import contents from "./file.txt";
console.log(contents); // => "Hello, world!"
.htmlHTML files are processed and any referenced assets (scripts, stylesheets, images) are bundled..cssCSS files are bundled together into a single .css file in the output directory..node .wasmThese files are supported by the Bun runtime, but during bundling they are treated as assets. ​Assets If the bundler encounters an import with an unrecognized extension, it treats the imported file as an external file. The referenced file is copied as-is into outdir, and the import is resolved as a path to the file. InputOutputCopy// bundle entrypoint import logo from "./logo.svg"; console.log(logo); The exact behavior of the file loader is also impacted by naming and publicPath. Refer to the Bundler > Loaders page for more complete documentation on the file loader. ​Plugins The behavior described in this table can be overridden or extended with plugins. Refer to the Bundler > Loaders page for complete documentation. ​API ​entrypoints Required An array of paths corresponding to the entrypoints of our application. One bundle will be generated for each entrypoint. JavaScript CLIbuild.tsCopyconst result = await Bun.build({ entrypoints: ["./index.ts"], }); // => { success: boolean, outputs: BuildArtifact[], logs: BuildMessage[] } terminalCopybun build ./index.ts ​files A map of file paths to their contents for in-memory bundling. This allows you to bundle virtual files that don’t exist on disk, or override the contents of files that do exist. This option is only available in the JavaScript API. File contents can be provided as a string, Blob, TypedArray, or ArrayBuffer. ​Bundle entirely from memory You can bundle code without any files on disk by providing all sources via files: build.tsCopyconst result = await Bun.build({ entrypoints: ["/app/index.ts"], files: { "/app/index.ts": ` import { greet } from "./greet.ts"; console.log(greet("World")); `, "/app/greet.ts": ` export function greet(name: string) { return "Hello, " + name + "!"; } `, }, }); const output = await result.outputs[0].text(); console.log(output); When all entrypoints are in the files map, the current working directory is used as the root. ​Override files on disk In-memory files take priority over files on disk. This lets you override specific files while keeping the rest of your codebase unchanged: build.tsCopy// Assume ./src/config.ts exists on disk with development settings await Bun.build({ entrypoints: ["./src/index.ts"], files: { // Override config.ts with production values "./src/config.ts": ` export const API_URL = "https://api.production.com"; export const DEBUG = false; `, }, outdir: "./dist", }); ​Mix disk and virtual files Real files on disk can import virtual files, and virtual files can import real files: build.tsCopy// ./src/index.ts exists on disk and imports "./generated.ts" await Bun.build({ entrypoints: ["./src/index.ts"], files: { // Provide a virtual file that index.ts imports "./src/generated.ts": ` export const BUILD_ID = "${crypto.randomUUID()}"; export const BUILD_TIME = ${Date.now()}; `, }, outdir: "./dist", }); This is useful for code generation, injecting build-time constants, or testing with mock modules. ​outdir The directory where output files will be written. JavaScript CLIbuild.tsCopyconst result = await Bun.build({ entrypoints: ['./index.ts'], outdir: './out' }); // => { success: boolean, outputs: BuildArtifact[], logs: BuildMessage[] } terminalCopybun build ./index.ts --outdir ./out If outdir is not passed to the JavaScript API, bundled code will not be written to disk. Bundled files are returned in an array of BuildArtifact objects. These objects are Blobs with extra properties; see Outputs for complete documentation. build.tsCopyconst result = await Bun.build({ entrypoints: ["./index.ts"], }); for (const res of result.outputs) { // Can be consumed as blobs await res.text(); // Bun will set Content-Type and Etag headers new Response(res); // Can be written manually, but you should use `outdir` in this case. Bun.write(path.join("out", res.path), res); } When outdir is set, the path property on a BuildArtifact will be the absolute path to where it was written to. ​target The intended execution environment for the bundle. JavaScript CLIbuild.tsCopyawait Bun.build({ entrypoints: ['./index.ts'], outdir: './out', target: 'browser', // default }) terminalCopybun build ./index.ts --outdir ./out --target browser Depending on the target, Bun will apply different module resolution rules and optimizations. browserDefault. For generating bundles that are intended for execution by a browser. Prioritizes the "browser" export condition when resolving imports. Importing any built-in modules, like node:events or node:path will work, but calling some functions, like fs.readFile will not work. bunFor generating bundles that are intended to be run by the Bun runtime. In many cases, it isn’t necessary to bundle server-side code; you can directly execute the source code without modification. However, bundling your server code can reduce startup times and improve running performance. This is the target to use for building full-stack applications with build-time HTML imports, where both server and client code are bundled together.All bundles generated with target: "bun" are marked with a special // @bun pragma, which indicates to the Bun runtime that there’s no need to re-transpile the file before execution.If any entrypoints contains a Bun shebang (#!/usr/bin/env bun) the bundler will default to target: "bun" instead of "browser".When using target: "bun" and format: "cjs" together, the // @bun @bun-cjs pragma is added and the CommonJS wrapper function is not compatible with Node.js. nodeFor generating bundles that are intended to be run by Node.js. Prioritizes the "node" export condition when resolving imports, and outputs .mjs. In the future, this will automatically polyfill the Bun global and other built-in bun:* modules, though this is not yet implemented. ​format Specifies the module format to be used in the generated bundles. Bun defaults to "esm", and provides experimental support for "cjs" and "iife". ​format: “esm” - ES Module This is the default format, which supports ES Module syntax including top-level await, import.meta, and more. JavaScript CLIbuild.tsCopyawait Bun.build({ entrypoints: ['./index.tsx'], outdir: './out', format: "esm", }) terminalCopybun build ./index.tsx --outdir ./out --format esm To use ES Module syntax in browsers, set format to "esm" and make sure your

智能索引记录