UNPKG

bun-types

Version:

Type definitions and documentation for Bun, an incredibly fast JavaScript runtime

1,415 lines (1,314 loc) โ€ข 324 kB
/** * Bun.js runtime APIs * * @example * * ```js * import {file} from 'bun'; * * // Log the file to the console * const input = await file('/path/to/file.txt').text(); * console.log(input); * ``` * * This module aliases `globalThis.Bun`. */ declare module "bun" { type PathLike = string | NodeJS.TypedArray | ArrayBufferLike | URL; type ArrayBufferView<TArrayBuffer extends ArrayBufferLike = ArrayBufferLike> = | NodeJS.TypedArray<TArrayBuffer> | DataView<TArrayBuffer>; type BufferSource = NodeJS.TypedArray<ArrayBufferLike> | DataView<ArrayBufferLike> | ArrayBufferLike; type StringOrBuffer = string | NodeJS.TypedArray | ArrayBufferLike; type XMLHttpRequestBodyInit = Blob | BufferSource | FormData | URLSearchParams | string; type ReadableStreamController<T> = ReadableStreamDefaultController<T>; type ReadableStreamDefaultReadResult<T> = | ReadableStreamDefaultReadValueResult<T> | ReadableStreamDefaultReadDoneResult; type ReadableStreamReader<T> = ReadableStreamDefaultReader<T>; type Transferable = ArrayBuffer | MessagePort; type MessageEventSource = Bun.__internal.UseLibDomIfAvailable<"MessageEventSource", undefined>; type Encoding = "utf-8" | "windows-1252" | "utf-16"; type UncaughtExceptionOrigin = "uncaughtException" | "unhandledRejection"; type MultipleResolveType = "resolve" | "reject"; type BeforeExitListener = (code: number) => void; type DisconnectListener = () => void; type ExitListener = (code: number) => void; type RejectionHandledListener = (promise: Promise<unknown>) => void; type FormDataEntryValue = File | string; type WarningListener = (warning: Error) => void; type MessageListener = (message: unknown, sendHandle: unknown) => void; type SignalsListener = (signal: NodeJS.Signals) => void; type BlobPart = string | Blob | BufferSource; type TimerHandler = (...args: any[]) => void; type DOMHighResTimeStamp = number; type EventListenerOrEventListenerObject = EventListener | EventListenerObject; type BlobOrStringOrBuffer = string | NodeJS.TypedArray | ArrayBufferLike | Blob; type MaybePromise<T> = T | Promise<T>; namespace __internal { type LibDomIsLoaded = typeof globalThis extends { onabort: any } ? true : false; /** * Helper type for avoiding conflicts in types. * * Uses the lib.dom.d.ts definition if it exists, otherwise defines it locally. * * This is to avoid type conflicts between lib.dom.d.ts and \@types/bun. * * Unfortunately some symbols cannot be defined when both Bun types and lib.dom.d.ts types are loaded, * and since we can't redeclare the symbol in a way that satisfies both, we need to fallback * to the type that lib.dom.d.ts provides. */ type UseLibDomIfAvailable<GlobalThisKeyName extends PropertyKey, Otherwise> = // `onabort` is defined in lib.dom.d.ts, so we can check to see if lib dom is loaded by checking if `onabort` is defined LibDomIsLoaded extends true ? typeof globalThis extends { [K in GlobalThisKeyName]: infer T } // if it is loaded, infer it from `globalThis` and use that value ? T : Otherwise // Not defined in lib dom (or anywhere else), so no conflict. We can safely use our own definition : Otherwise; // Lib dom not loaded anyway, so no conflict. We can safely use our own definition /** * Like Omit, but correctly distributes over unions. Most useful for removing * properties from union options objects, like {@link Bun.SQL.Options} * * @example * ```ts * type X = Bun.DistributedOmit<{type?: 'a', url?: string} | {type?: 'b', flag?: boolean}, "url"> * // `{type?: 'a'} | {type?: 'b', flag?: boolean}` (Omit applied to each union item instead of entire type) * * type X = Omit<{type?: 'a', url?: string} | {type?: 'b', flag?: boolean}, "url">; * // `{type?: "a" | "b" | undefined}` (Missing `flag` property and no longer a union) * ``` */ type DistributedOmit<T, K extends PropertyKey> = T extends T ? Omit<T, K> : never; type KeysInBoth<A, B> = Extract<keyof A, keyof B>; type MergeInner<A, B> = Omit<A, KeysInBoth<A, B>> & Omit<B, KeysInBoth<A, B>> & { [Key in KeysInBoth<A, B>]: A[Key] | B[Key]; }; type Merge<A, B> = MergeInner<A, B> & MergeInner<B, A>; type DistributedMerge<T, Else = T> = T extends T ? Merge<T, Exclude<Else, T>> : never; type Without<A, B> = A & { [Key in Exclude<keyof B, keyof A>]?: never; }; type XOR<A, B> = Without<A, B> | Without<B, A>; } interface ErrorEventInit extends EventInit { colno?: number; error?: any; filename?: string; lineno?: number; message?: string; } interface CloseEventInit extends EventInit { code?: number; reason?: string; wasClean?: boolean; } interface MessageEventInit<T = any> extends EventInit { data?: T; lastEventId?: string; origin?: string; source?: Bun.MessageEventSource | null; } interface EventInit { bubbles?: boolean; cancelable?: boolean; composed?: boolean; } interface EventListenerOptions { capture?: boolean; } interface CustomEventInit<T = any> extends Bun.EventInit { detail?: T; } /** A message received by a target object. */ interface BunMessageEvent<T = any> extends Event { /** Returns the data of the message. */ readonly data: T; /** Returns the last event ID string, for server-sent events. */ readonly lastEventId: string; /** Returns the origin of the message, for server-sent events and cross-document messaging. */ readonly origin: string; /** Returns the MessagePort array sent with the message, for cross-document messaging and channel messaging. */ readonly ports: readonly MessagePort[]; // ReadonlyArray<typeof import("worker_threads").MessagePort["prototype"]>; readonly source: Bun.MessageEventSource | null; } type MessageEvent<T = any> = Bun.__internal.UseLibDomIfAvailable<"MessageEvent", BunMessageEvent<T>>; interface ReadableStreamDefaultReadManyResult<T> { done: boolean; /** Number of bytes */ size: number; value: T[]; } interface EventSourceEventMap { error: Event; message: MessageEvent; open: Event; } interface AddEventListenerOptions extends EventListenerOptions { /** When `true`, the listener is automatically removed when it is first invoked. Default: `false`. */ once?: boolean; /** When `true`, serves as a hint that the listener will not call the `Event` object's `preventDefault()` method. Default: false. */ passive?: boolean; signal?: AbortSignal; } interface EventListener { (evt: Event): void; } interface EventListenerObject { handleEvent(object: Event): void; } interface FetchEvent extends Event { readonly request: Request; readonly url: string; waitUntil(promise: Promise<any>): void; respondWith(response: Response | Promise<Response>): void; } interface EventMap { fetch: FetchEvent; message: MessageEvent; messageerror: MessageEvent; // exit: Event; } interface StructuredSerializeOptions { transfer?: Bun.Transferable[]; } interface EventSource extends EventTarget { new (url: string | URL, eventSourceInitDict?: EventSourceInit): EventSource; onerror: ((this: EventSource, ev: Event) => any) | null; onmessage: ((this: EventSource, ev: MessageEvent) => any) | null; onopen: ((this: EventSource, ev: Event) => any) | null; /** Returns the state of this EventSource object's connection. It can have the values described below. */ readonly readyState: number; /** Returns the URL providing the event stream. */ readonly url: string; /** Returns true if the credentials mode for connection requests to the URL providing the event stream is set to "include", and false otherwise. * * Not supported in Bun */ readonly withCredentials: boolean; /** Aborts any instances of the fetch algorithm started for this EventSource object, and sets the readyState attribute to CLOSED. */ close(): void; readonly CLOSED: 2; readonly CONNECTING: 0; readonly OPEN: 1; addEventListener<K extends keyof EventSourceEventMap>( type: K, listener: (this: EventSource, ev: EventSourceEventMap[K]) => any, options?: boolean | AddEventListenerOptions, ): void; addEventListener( type: string, listener: (this: EventSource, event: MessageEvent) => any, options?: boolean | AddEventListenerOptions, ): void; addEventListener( type: string, listener: EventListenerOrEventListenerObject, options?: boolean | AddEventListenerOptions, ): void; removeEventListener<K extends keyof EventSourceEventMap>( type: K, listener: (this: EventSource, ev: EventSourceEventMap[K]) => any, options?: boolean | EventListenerOptions, ): void; removeEventListener( type: string, listener: (this: EventSource, event: MessageEvent) => any, options?: boolean | EventListenerOptions, ): void; removeEventListener( type: string, listener: EventListenerOrEventListenerObject, options?: boolean | EventListenerOptions, ): void; /** * Keep the event loop alive while connection is open or reconnecting * * Not available in browsers */ ref(): void; /** * Do not keep the event loop alive while connection is open or reconnecting * * Not available in browsers */ unref(): void; } interface TransformerFlushCallback<O> { (controller: TransformStreamDefaultController<O>): void | PromiseLike<void>; } interface TransformerStartCallback<O> { (controller: TransformStreamDefaultController<O>): any; } interface TransformerTransformCallback<I, O> { (chunk: I, controller: TransformStreamDefaultController<O>): void | PromiseLike<void>; } interface UnderlyingSinkAbortCallback { (reason?: any): void | PromiseLike<void>; } interface UnderlyingSinkCloseCallback { (): void | PromiseLike<void>; } interface UnderlyingSinkStartCallback { (controller: WritableStreamDefaultController): any; } interface UnderlyingSinkWriteCallback<W> { (chunk: W, controller: WritableStreamDefaultController): void | PromiseLike<void>; } interface UnderlyingSourceCancelCallback { (reason?: any): void | PromiseLike<void>; } interface UnderlyingSink<W = any> { abort?: UnderlyingSinkAbortCallback; close?: UnderlyingSinkCloseCallback; start?: UnderlyingSinkStartCallback; type?: undefined | "default" | "bytes"; write?: UnderlyingSinkWriteCallback<W>; } interface UnderlyingSource<R = any> { cancel?: UnderlyingSourceCancelCallback; pull?: UnderlyingSourcePullCallback<R>; start?: UnderlyingSourceStartCallback<R>; /** * Mode "bytes" is not currently supported. */ type?: undefined; } interface DirectUnderlyingSource<R = any> { cancel?: UnderlyingSourceCancelCallback; pull: (controller: ReadableStreamDirectController) => void | PromiseLike<void>; type: "direct"; } interface UnderlyingSourcePullCallback<R> { (controller: ReadableStreamController<R>): void | PromiseLike<void>; } interface UnderlyingSourceStartCallback<R> { (controller: ReadableStreamController<R>): any; } interface GenericTransformStream { readonly readable: ReadableStream; readonly writable: WritableStream; } interface AbstractWorkerEventMap { error: ErrorEvent; } interface WorkerEventMap extends AbstractWorkerEventMap { message: MessageEvent; messageerror: MessageEvent; close: CloseEvent; open: Event; } type WorkerType = "classic" | "module"; interface AbstractWorker { /** [MDN Reference](https://developer.mozilla.org/docs/Web/API/ServiceWorker/error_event) */ onerror: ((this: AbstractWorker, ev: ErrorEvent) => any) | null; addEventListener<K extends keyof AbstractWorkerEventMap>( type: K, listener: (this: AbstractWorker, ev: AbstractWorkerEventMap[K]) => any, options?: boolean | AddEventListenerOptions, ): void; addEventListener( type: string, listener: EventListenerOrEventListenerObject, options?: boolean | AddEventListenerOptions, ): void; removeEventListener<K extends keyof AbstractWorkerEventMap>( type: K, listener: (this: AbstractWorker, ev: AbstractWorkerEventMap[K]) => any, options?: boolean | EventListenerOptions, ): void; removeEventListener( type: string, listener: EventListenerOrEventListenerObject, options?: boolean | EventListenerOptions, ): void; } /** * Bun's Web Worker constructor supports some extra options on top of the API browsers have. */ interface WorkerOptions { /** * A string specifying an identifying name for the DedicatedWorkerGlobalScope representing the scope of * the worker, which is mainly useful for debugging purposes. */ name?: string; /** * Use less memory, but make the worker slower. * * Internally, this sets the heap size configuration in JavaScriptCore to be * the small heap instead of the large heap. */ smol?: boolean; /** * When `true`, the worker will keep the parent thread alive until the worker is terminated or `unref`'d. * When `false`, the worker will not keep the parent thread alive. * * By default, this is `false`. */ ref?: boolean; /** * In Bun, this does nothing. */ type?: Bun.WorkerType | undefined; /** * List of arguments which would be stringified and appended to * `Bun.argv` / `process.argv` in the worker. This is mostly similar to the `data` * but the values will be available on the global `Bun.argv` as if they * were passed as CLI options to the script. */ argv?: any[] | undefined; /** If `true` and the first argument is a string, interpret the first argument to the constructor as a script that is executed once the worker is online. */ // eval?: boolean | undefined; /** * If set, specifies the initial value of process.env inside the Worker thread. As a special value, worker.SHARE_ENV may be used to specify that the parent thread and the child thread should share their environment variables; in that case, changes to one thread's process.env object affect the other thread as well. Default: process.env. */ env?: Record<string, string> | (typeof import("node:worker_threads"))["SHARE_ENV"] | undefined; /** * In Bun, this does nothing. */ credentials?: import("undici-types").RequestCredentials | undefined; /** * @default true */ // trackUnmanagedFds?: boolean; // resourceLimits?: import("worker_threads").ResourceLimits; /** * An array of module specifiers to preload in the worker. * * These modules load before the worker's entry point is executed. * * Equivalent to passing the `--preload` CLI argument, but only for this Worker. */ preload?: string[] | string | undefined; } interface Worker extends EventTarget, AbstractWorker { /** [MDN Reference](https://developer.mozilla.org/docs/Web/API/Worker/message_event) */ onmessage: ((this: Worker, ev: MessageEvent) => any) | null; /** [MDN Reference](https://developer.mozilla.org/docs/Web/API/Worker/messageerror_event) */ onmessageerror: ((this: Worker, ev: MessageEvent) => any) | null; /** * Clones message and transmits it to worker's global environment. transfer can be passed as a list of objects that are to be transferred rather than cloned. * * [MDN Reference](https://developer.mozilla.org/docs/Web/API/Worker/postMessage) */ postMessage(message: any, transfer: Transferable[]): void; postMessage(message: any, options?: StructuredSerializeOptions): void; /** * Aborts worker's associated global environment. * * [MDN Reference](https://developer.mozilla.org/docs/Web/API/Worker/terminate) */ terminate(): void; addEventListener<K extends keyof WorkerEventMap>( type: K, listener: (this: Worker, ev: WorkerEventMap[K]) => any, options?: boolean | AddEventListenerOptions, ): void; addEventListener( type: string, listener: EventListenerOrEventListenerObject, options?: boolean | AddEventListenerOptions, ): void; removeEventListener<K extends keyof WorkerEventMap>( type: K, listener: (this: Worker, ev: WorkerEventMap[K]) => any, options?: boolean | EventListenerOptions, ): void; removeEventListener( type: string, listener: EventListenerOrEventListenerObject, options?: boolean | EventListenerOptions, ): void; /** * Opposite of `unref()`, calling `ref()` on a previously `unref()`ed worker does _not_ let the program exit if it's the only active handle left (the default * behavior). If the worker is `ref()`ed, calling `ref()` again has * no effect. * @since v10.5.0 */ ref(): void; /** * Calling `unref()` on a worker allows the thread to exit if this is the only * active handle in the event system. If the worker is already `unref()`ed calling`unref()` again has no effect. * @since v10.5.0 */ unref(): void; /** * An integer identifier for the referenced thread. Inside the worker thread, * it is available as `require('node:worker_threads').threadId`. * This value is unique for each `Worker` instance inside a single process. * @since v10.5.0 */ threadId: number; } interface Env { NODE_ENV?: string; /** * Can be used to change the default timezone at runtime */ TZ?: string; } /** * The environment variables of the process * * Defaults to `process.env` as it was when the current Bun process launched. * * Changes to `process.env` at runtime won't automatically be reflected in the default value. For that, you can pass `process.env` explicitly. */ const env: Env & NodeJS.ProcessEnv & ImportMetaEnv; /** * The raw arguments passed to the process, including flags passed to Bun. If you want to easily read flags passed to your script, consider using `process.argv` instead. */ const argv: string[]; interface WhichOptions { /** * Overrides the PATH environment variable */ PATH?: string; /** * When given a relative path, use this path to join it. */ cwd?: string; } /** * Find the path to an executable, similar to typing which in your terminal. Reads the `PATH` environment variable unless overridden with `options.PATH`. * * @category Utilities * * @param command The name of the executable or script to find * @param options Options for the search */ function which(command: string, options?: WhichOptions): string | null; interface StringWidthOptions { /** * If `true`, count ANSI escape codes as part of the string width. If `false`, ANSI escape codes are ignored when calculating the string width. * * @default false */ countAnsiEscapeCodes?: boolean; /** * When it's ambiugous and `true`, count emoji as 1 characters wide. If `false`, emoji are counted as 2 character wide. * * @default true */ ambiguousIsNarrow?: boolean; } /** * Get the column count of a string as it would be displayed in a terminal. * Supports ANSI escape codes, emoji, and wide characters. * * This is useful for: * - Aligning text in a terminal * - Quickly checking if a string contains ANSI escape codes * - Measuring the width of a string in a terminal * * This API is designed to match the popular "string-width" package, so that * existing code can be easily ported to Bun and vice versa. * * @returns The width of the string in columns * * @example * ```ts * import { stringWidth } from "bun"; * * console.log(stringWidth("abc")); // 3 * console.log(stringWidth("๐Ÿ‘ฉโ€๐Ÿ‘ฉโ€๐Ÿ‘งโ€๐Ÿ‘ฆ")); // 1 * console.log(stringWidth("\u001b[31mhello\u001b[39m")); // 5 * console.log(stringWidth("\u001b[31mhello\u001b[39m", { countAnsiEscapeCodes: false })); // 5 * console.log(stringWidth("\u001b[31mhello\u001b[39m", { countAnsiEscapeCodes: true })); // 13 * ``` */ function stringWidth( /** * The string to measure */ input: string, options?: StringWidthOptions, ): number; /** * Remove ANSI escape codes from a string. * * @category Utilities * * @param input The string to remove ANSI escape codes from. * @returns The string with ANSI escape codes removed. * * @example * ```ts * import { stripANSI } from "bun"; * * console.log(stripANSI("\u001b[31mhello\u001b[39m")); // "hello" * ``` */ function stripANSI(input: string): string; interface SliceAnsiOptions { /** * If set, and content was cut at either edge of the requested range, * insert this string at the cut edge(s). The ellipsis is counted against * the visible-width budget and is emitted *inside* any active SGR styles * (color, bold, etc.) so it inherits them, but *outside* any active OSC 8 * hyperlink. * * This turns `sliceAnsi` into a drop-in `cli-truncate` replacement: * - truncate-end: `sliceAnsi(str, 0, max, { ellipsis: "\u2026" })` * - truncate-start: `sliceAnsi(str, -max, undefined, { ellipsis: "\u2026" })` */ ellipsis?: string; /** * Count characters with East Asian Width "Ambiguous" as 1 column (narrow) * instead of 2 (wide). Affects Greek, Cyrillic, some symbols, etc. that * render wide in CJK-encoded terminals but narrow in Western ones. * * Matches the option of the same name in {@link stringWidth} and * {@link wrapAnsi}. * * @default true */ ambiguousIsNarrow?: boolean; } /** * Slice a string by visible column width, preserving ANSI escape codes. * * Like `String.prototype.slice`, but indices are terminal column widths * (accounting for wide CJK characters, emoji grapheme clusters, and * zero-width joiners), and ANSI escape sequences (SGR colors, OSC 8 * hyperlinks, etc.) are preserved and correctly re-opened/closed at the * slice boundaries. * * @category Utilities * * @param input The string to slice * @param start Starting column (default 0). Negative counts from end. * @param end Ending column, exclusive (default end of string). Negative counts from end. * @param options Optional behavior flags (e.g. `ellipsis` for truncation) * @returns The sliced string with ANSI codes intact * * @example * ```ts * import { sliceAnsi } from "bun"; * * // Plain slice (replaces the `slice-ansi` npm package) * sliceAnsi("hello", 1, 4); // "ell" * sliceAnsi("\u001b[31mhello\u001b[39m", 1, 4); // "\u001b[31mell\u001b[39m" * sliceAnsi("\u5b89\u5b81\u54c8", 0, 4); // "\u5b89\u5b81" (CJK: width 2 each) * * // Truncation (replaces the `cli-truncate` npm package) * sliceAnsi("unicorn", 0, 4, "\u2026"); // "uni\u2026" * sliceAnsi("unicorn", -4, undefined, "\u2026"); // "\u2026orn" * ``` */ function sliceAnsi( input: string, start?: number, end?: number, /** * Shorthand for common options (avoids `{}` allocation): * - `string` โ†’ ellipsis (equivalent to `{ ellipsis: string }`) * - `boolean` โ†’ ambiguousIsNarrow (equivalent to `{ ambiguousIsNarrow: boolean }`) * - `SliceAnsiOptions` โ†’ full options object */ options?: string | boolean | SliceAnsiOptions, /** * ambiguousIsNarrow as a positional arg, usable when the 4th arg is an * ellipsis string (or `undefined`). Lets you pass both options without * an object: `sliceAnsi(s, 0, n, "\u2026", false)`. */ ambiguousIsNarrow?: boolean, ): string; interface WrapAnsiOptions { /** * If `true`, break words in the middle if they don't fit on a line. * If `false`, only break at word boundaries. * * @default false */ hard?: boolean; /** * If `true`, wrap at word boundaries when possible. * If `false`, don't perform word wrapping (only wrap at explicit newlines). * * @default true */ wordWrap?: boolean; /** * If `true`, trim leading and trailing whitespace from each line. * If `false`, preserve whitespace. * * @default true */ trim?: boolean; /** * When it's ambiguous and `true`, count ambiguous width characters as 1 character wide. * If `false`, count them as 2 characters wide. * * @default true */ ambiguousIsNarrow?: boolean; } /** * Wrap a string to fit within the specified column width, preserving ANSI escape codes. * * This function is designed to be compatible with the popular "wrap-ansi" NPM package. * * Features: * - Preserves ANSI escape codes (colors, styles) across line breaks * - Supports SGR codes (colors, bold, italic, etc.) and OSC 8 hyperlinks * - Respects Unicode display widths (full-width characters, emoji) * - Word wrapping at word boundaries (configurable) * * @category Utilities * * @param input The string to wrap * @param columns The maximum column width * @param options Wrapping options * @returns The wrapped string * * @example * ```ts * import { wrapAnsi } from "bun"; * * console.log(wrapAnsi("hello world", 5)); * // Output: * // hello * // world * * // Preserves ANSI colors across line breaks * console.log(wrapAnsi("\u001b[31mhello world\u001b[0m", 5)); * // Output: * // \u001b[31mhello\u001b[0m * // \u001b[31mworld\u001b[0m * * // Hard wrap long words * console.log(wrapAnsi("abcdefghij", 3, { hard: true })); * // Output: * // abc * // def * // ghi * // j * ``` */ function wrapAnsi( /** * The string to wrap */ input: string, /** * The maximum column width */ columns: number, /** * Wrapping options */ options?: WrapAnsiOptions, ): string; /** * TOML related APIs */ namespace TOML { /** * Parse a TOML string into a JavaScript object. * * @category Utilities * * @param input The TOML string to parse * @returns A JavaScript object */ export function parse(input: string): object; } /** * JSONC related APIs */ namespace JSONC { /** * Parse a JSONC (JSON with Comments) string into a JavaScript value. * * Supports both single-line (`//`) and block comments (`/* ... *\/`), as well as * trailing commas in objects and arrays. * * @category Utilities * * @param input The JSONC string to parse * @returns A JavaScript value * * @example * ```js * const result = Bun.JSONC.parse(`{ * // This is a comment * "name": "my-app", * "version": "1.0.0", // trailing comma is allowed * }`); * ``` */ export function parse(input: string): unknown; } /** * JSONL (JSON Lines) related APIs. * * Each line in the input is expected to be a valid JSON value separated by newlines. */ namespace JSONL { /** * The result of `Bun.JSONL.parseChunk`. */ interface ParseChunkResult { /** The successfully parsed JSON values. */ values: unknown[]; /** How far into the input was consumed. When the input is a string, this is a character offset. When the input is a `TypedArray`, this is a byte offset. Use `input.slice(read)` or `input.subarray(read)` to get the unconsumed remainder. */ read: number; /** `true` if all input was consumed successfully. `false` if the input ends with an incomplete value or a parse error occurred. */ done: boolean; /** A `SyntaxError` if a parse error occurred, otherwise `null`. Values parsed before the error are still available in `values`. */ error: SyntaxError | null; } /** * Parse a JSONL (JSON Lines) string into an array of JavaScript values. * * If a parse error occurs and no values were successfully parsed, throws * a `SyntaxError`. If values were parsed before the error, returns the * successfully parsed values without throwing. * * Incomplete trailing values (e.g. from a partial chunk) are silently * ignored and not included in the result. * * When a `TypedArray` is passed, the bytes are parsed directly without * copying if the content is ASCII. * * @param input The JSONL string or typed array to parse * @returns An array of parsed values * @throws {SyntaxError} If the input starts with invalid JSON and no values could be parsed * * @example * ```js * const items = Bun.JSONL.parse('{"a":1}\n{"b":2}\n'); * // [{ a: 1 }, { b: 2 }] * * // From a Uint8Array (zero-copy for ASCII): * const buf = new TextEncoder().encode('{"a":1}\n{"b":2}\n'); * const items = Bun.JSONL.parse(buf); * // [{ a: 1 }, { b: 2 }] * * // Partial results on error after valid values: * const partial = Bun.JSONL.parse('{"a":1}\n{bad}\n'); * // [{ a: 1 }] * * // Throws when no valid values precede the error: * Bun.JSONL.parse('{bad}\n'); // throws SyntaxError * ``` */ export function parse(input: string | NodeJS.TypedArray | DataView<ArrayBuffer> | ArrayBufferLike): unknown[]; /** * Parse a JSONL chunk, designed for streaming use. * * Never throws on parse errors. Instead, returns whatever values were * successfully parsed along with an `error` property containing the * `SyntaxError` (or `null` on success). Use `read` to determine how * much input was consumed and `done` to check if all input was parsed. * * When a `TypedArray` is passed, the bytes are parsed directly without * copying if the content is ASCII. Optional `start` and `end` parameters * select a window of the input without copying. For typed arrays these * are byte offsets and `read` will be a byte offset into the original * typed array. For strings these are character offsets and `read` will * be a character offset into the original string. * * @param input The JSONL string or typed array to parse * @param start Offset to start parsing from (bytes for typed arrays, characters for strings, default: 0) * @param end Offset to stop parsing at (bytes for typed arrays, characters for strings, default: input length) * @returns An object with `values`, `read`, `done`, and `error` properties * * @example * ```js * let buffer = new Uint8Array(0); * for await (const chunk of stream) { * buffer = Buffer.concat([buffer, chunk]); * const { values, read, error } = Bun.JSONL.parseChunk(buffer); * if (error) throw error; * for (const value of values) handle(value); * buffer = buffer.subarray(read); * } * ``` */ export function parseChunk( input: string | NodeJS.TypedArray | DataView<ArrayBuffer> | ArrayBufferLike, start?: number, end?: number, ): ParseChunkResult; } /** * YAML related APIs */ namespace YAML { /** * Parse a YAML string into a JavaScript value * * @category Utilities * * @param input The YAML string to parse * @returns A JavaScript value * * @example * ```ts * import { YAML } from "bun"; * * console.log(YAML.parse("123")) // 123 * console.log(YAML.parse("null")) // null * console.log(YAML.parse("false")) // false * console.log(YAML.parse("abc")) // "abc" * console.log(YAML.parse("- abc")) // [ "abc" ] * console.log(YAML.parse("abc: def")) // { "abc": "def" } * ``` */ export function parse(input: string): unknown; /** * Convert a JavaScript value into a YAML string. Strings are double quoted if they contain keywords, non-printable or * escaped characters, or if a YAML parser would parse them as numbers. Anchors and aliases are inferred from objects, allowing cycles. * * @category Utilities * * @param input The JavaScript value to stringify. * @param replacer Currently not supported. * @param space A number for how many spaces each level of indentation gets, or a string used as indentation. * Without this parameter, outputs flow-style (single-line) YAML. * With this parameter, outputs block-style (multi-line) YAML. * The number is clamped between 0 and 10, and the first 10 characters of the string are used. * @returns A string containing the YAML document. * * @example * ```ts * import { YAML } from "bun"; * * const input = { * abc: "def", * num: 123 * }; * * // Without space - flow style (single-line) * console.log(YAML.stringify(input)); * // {abc: def,num: 123} * * // With space - block style (multi-line) * console.log(YAML.stringify(input, null, 2)); * // abc: def * // num: 123 * * const cycle = {}; * cycle.obj = cycle; * console.log(YAML.stringify(cycle, null, 2)); * // &1 * // obj: *1 */ export function stringify(input: unknown, replacer?: undefined | null, space?: string | number): string; } /** * Markdown related APIs. * * Provides fast markdown parsing and rendering with three output modes: * - `html()` โ€” render to an HTML string * - `render()` โ€” render with custom callbacks for each element * - `react()` โ€” parse to React-compatible JSX elements * * Supports GFM extensions (tables, strikethrough, task lists, autolinks) and * component overrides to replace default HTML tags with custom components. * * @example * ```tsx * // Render markdown to HTML * const html = Bun.markdown.html("# Hello **world**"); * // "<h1>Hello <strong>world</strong></h1>\n" * * // Render with custom callbacks * const ansi = Bun.markdown.render("# Hello **world**", { * heading: (children, { level }) => `\x1b[1m${children}\x1b[0m\n`, * strong: (children) => `\x1b[1m${children}\x1b[22m`, * paragraph: (children) => children + "\n", * }); * * // Render as a React component * function Markdown({ text }: { text: string }) { * return Bun.markdown.react(text); * } * * // With component overrides * const element = Bun.markdown.react("# Hello", { h1: MyHeadingComponent }); * ``` */ namespace markdown { /** * Options for configuring the markdown parser. * * By default, GFM extensions (tables, strikethrough, task lists) are enabled. */ interface Options { /** Enable GFM tables. Default: `true`. */ tables?: boolean; /** Enable GFM strikethrough (`~~text~~`). Default: `true`. */ strikethrough?: boolean; /** Enable GFM task lists (`- [x] item`). Default: `true`. */ tasklists?: boolean; /** Treat soft line breaks as hard line breaks. Default: `false`. */ hardSoftBreaks?: boolean; /** Enable wiki-style links (`[[target]]` or `[[target|label]]`). Default: `false`. */ wikiLinks?: boolean; /** Enable underline syntax (`__text__` renders as `<u>` instead of `<strong>`). Default: `false`. */ underline?: boolean; /** Enable LaTeX math (`$inline$` and `$$display$$`). Default: `false`. */ latexMath?: boolean; /** Collapse whitespace in text content. Default: `false`. */ collapseWhitespace?: boolean; /** Allow ATX headers without a space after `#`. Default: `false`. */ permissiveAtxHeaders?: boolean; /** Disable indented code blocks. Default: `false`. */ noIndentedCodeBlocks?: boolean; /** Disable HTML blocks. Default: `false`. */ noHtmlBlocks?: boolean; /** Disable inline HTML spans. Default: `false`. */ noHtmlSpans?: boolean; /** * Enable the GFM tag filter, which replaces `<` with `&lt;` for disallowed * HTML tags (e.g. `<script>`, `<style>`, `<iframe>`). Default: `false`. */ tagFilter?: boolean; /** * Enable autolinks. Pass `true` to enable all autolink types (URL, WWW, email), * or an object to enable individually. * * @example * ```ts * // Enable all autolinks * { autolinks: true } * // Enable only URL and email autolinks * { autolinks: { url: true, email: true } } * ``` */ autolinks?: boolean | { url?: boolean; www?: boolean; email?: boolean }; /** * Configure heading IDs and autolink headings. Pass `true` to enable both * heading IDs and autolink headings, or an object to configure individually. * * @example * ```ts * // Enable both heading IDs and autolink headings * { headings: true } * // Enable only heading IDs * { headings: { ids: true } } * ``` */ headings?: boolean | { ids?: boolean; autolink?: boolean }; } /** A component that accepts props `P`: a function, class, or HTML tag name. */ type Component<P = {}> = string | ((props: P) => any) | (new (props: P) => any); interface ChildrenProps { children: import("./jsx.d.ts").JSX.Element[]; } interface HeadingProps extends ChildrenProps { /** Heading ID slug. Set when `headings: { ids: true }` is enabled. */ id?: string; } interface OrderedListProps extends ChildrenProps { /** The start number. */ start: number; } interface ListItemProps extends ChildrenProps { /** Task list checked state. Set for `- [x]` / `- [ ]` items. */ checked?: boolean; } interface CodeBlockProps extends ChildrenProps { /** The info-string language (e.g. `"js"`). */ language?: string; } interface CellProps extends ChildrenProps { /** Column alignment. */ align?: "left" | "center" | "right"; } interface LinkProps extends ChildrenProps { /** Link URL. */ href: string; /** Link title attribute. */ title?: string; } interface ImageProps { /** Image URL. */ src: string; /** Alt text. */ alt?: string; /** Image title attribute. */ title?: string; } /** * Component overrides for `react()`. * * Replace default HTML tags with custom React components. Each override * receives the same props the default element would get. * * @example * ```tsx * function Code({ language, children }: { language?: string; children: React.ReactNode }) { * return <pre data-language={language}><code>{children}</code></pre>; * } * Bun.markdown.react(text, { pre: Code }); * ``` */ interface ComponentOverrides { h1?: Component<HeadingProps>; h2?: Component<HeadingProps>; h3?: Component<HeadingProps>; h4?: Component<HeadingProps>; h5?: Component<HeadingProps>; h6?: Component<HeadingProps>; p?: Component<ChildrenProps>; blockquote?: Component<ChildrenProps>; ul?: Component<ChildrenProps>; ol?: Component<OrderedListProps>; li?: Component<ListItemProps>; pre?: Component<CodeBlockProps>; hr?: Component<{}>; html?: Component<ChildrenProps>; table?: Component<ChildrenProps>; thead?: Component<ChildrenProps>; tbody?: Component<ChildrenProps>; tr?: Component<ChildrenProps>; th?: Component<CellProps>; td?: Component<CellProps>; em?: Component<ChildrenProps>; strong?: Component<ChildrenProps>; a?: Component<LinkProps>; img?: Component<ImageProps>; code?: Component<ChildrenProps>; del?: Component<ChildrenProps>; math?: Component<ChildrenProps>; u?: Component<ChildrenProps>; br?: Component<{}>; } /** * Callbacks for `render()`. Each callback receives the accumulated children * as a string and optional metadata, and returns a string. * * Return `null` or `undefined` to omit the element from the output. * If no callback is registered for an element, its children pass through unchanged. */ /** Meta passed to the `heading` callback. */ interface HeadingMeta { /** Heading level (1โ€“6). */ level: number; /** Heading ID slug. Set when `headings: { ids: true }` is enabled. */ id?: string; } /** Meta passed to the `code` callback. */ interface CodeBlockMeta { /** The info-string language (e.g. `"js"`). */ language?: string; } /** Meta passed to the `list` callback. */ interface ListMeta { /** Whether this is an ordered list. */ ordered: boolean; /** The start number for ordered lists. */ start?: number; /** Nesting depth. `0` for a top-level list, `1` for a list inside a list item, etc. */ depth: number; } /** Meta passed to the `listItem` callback. */ interface ListItemMeta { /** 0-based index of this item within its parent list. */ index: number; /** Nesting depth of the parent list. `0` for items in a top-level list. */ depth: number; /** Whether the parent list is ordered. */ ordered: boolean; /** The start number of the parent list (only set when `ordered` is true). */ start?: number; /** Task list checked state. Set for `- [x]` / `- [ ]` items. */ checked?: boolean; } /** Meta passed to `th` and `td` callbacks. */ interface CellMeta { /** Column alignment. */ align?: "left" | "center" | "right"; } /** Meta passed to the `link` callback. */ interface LinkMeta { /** Link URL. */ href: string; /** Link title attribute. */ title?: string; } /** Meta passed to the `image` callback. */ interface ImageMeta { /** Image URL. */ src: string; /** Image title attribute. */ title?: string; } interface RenderCallbacks { /** Heading (level 1โ€“6). `id` is set when `headings: { ids: true }` is enabled. */ heading?: (children: string, meta: HeadingMeta) => string | null | undefined; /** Paragraph. */ paragraph?: (children: string) => string | null | undefined; /** Blockquote. */ blockquote?: (children: string) => string | null | undefined; /** Code block. `meta.language` is the info-string (e.g. `"js"`). Only passed for fenced code blocks with a language. */ code?: (children: string, meta?: CodeBlockMeta) => string | null | undefined; /** Ordered or unordered list. `start` is the first item number for ordered lists. */ list?: (children: string, meta: ListMeta) => string | null | undefined; /** List item. `meta` always includes `{index, depth, ordered}`. `meta.start` is set for ordered lists; `meta.checked` is set for task list items. */ listItem?: (children: string, meta: ListItemMeta) => string | null | undefined; /** Horizontal rule. */ hr?: (children: string) => string | null | undefined; /** Table. */ table?: (children: string) => string | null | undefined; /** Table head. */ thead?: (children: string) => string | null | undefined; /** Table body. */ tbody?: (children: string) => string | null | undefined; /** Table row. */ tr?: (children: string) => string | null | undefined; /** Table header cell. `meta.align` is set when column alignment is specified. */ th?: (children: string, meta?: CellMeta) => string | null | undefined; /** Table data cell. `meta.align` is set when column alignment is specified. */ td?: (children: string, meta?: CellMeta) => string | null | undefined; /** Raw HTML content. */ html?: (children: string) => string | null | undefined; /** Strong emphasis (`**text**`). */ strong?: (children: string) => string | null | undefined; /** Emphasis (`*text*`). */ emphasis?: (children: string) => string | null | undefined; /** Link. `href` is the URL, `title` is the optional title attribute. */ link?: (children: string, meta: LinkMeta) => string | null | undefined; /** Image. `src` is the URL, `title` is the optional title attribute. */ image?: (children: string, meta: ImageMeta) => string | null | undefined; /** Inline code (`` `code` ``). */ codespan?: (children: string) => string | null | undefined; /** Strikethrough (`~~text~~`). */ strikethrough?: (children: string) => string | null | undefined; /** Plain text content. */ text?: (text: string) => string | null | undefined; } /** Options for `react()` โ€” parser options and element symbol configuration. */ interface ReactOptions extends Options { /** * Which `$$typeof` symbol to use on the generated elements. * - `19` (default): `Symbol.for('react.transitional.element')` * - `18`: `Symbol.for('react.element')` โ€” use this for React 18 and older */ reactVersion?: 18 | 19; } /** * Render markdown to an HTML string. * * @param input The markdown string or buffer to render * @param options Parser options * @returns An HTML string * * @example * ```ts * const html = Bun.markdown.html("# Hello **world**"); * // "<h1>Hello <strong>world</strong></h1>\n" * * // With options * const html = Bun.markdown.html("## Hello", { headings: { ids: true } }); * // '<h2 id="hello">Hello</h2>\n' * ``` */ export function html( input: string | NodeJS.TypedArray | DataView<ArrayBuffer> | ArrayBufferLike, options?: Options, ): string; /** * Theme for ANSI terminal rendering. */ export interface AnsiTheme { /** * Emit ANSI color + styling escape sequences. When `false`, the * renderer falls back to plain ASCII chrome (no box drawing, * no emoji, no escape codes). * @default true */ colors?: boolean; /** * Emit OSC 8 hyperlinks (clickable links in modern terminals). * When `false`, links render as `text (url)`. * @default false */ hyperlinks?: boolean; /** * True when the terminal background is light. Affects the color * palette chosen for inline code backgrounds. Defaults to * detecting from the `COLORFGBG` environment variable. */ light?: boolean; /** * Line width used for word-wrapping paragraphs and headings and * for the horizontal rule. Pass `0` to disable wrapping. * @default 80 */ columns?: number; /** * Inline images using the Kitty Graphics Protocol when the `src` * resolves to a local file on disk. Falls through to the text alt * for remote URLs. Supported by Kitty, WezTerm, and Ghostty. * @default false */ kittyGraphics?: boolean; } /** * Render markdown to an ANSI-colored terminal string. * * Supports headings, lists, tables, inline styles, syntax-highlighted * code blocks, links, images, and blockquotes. By default, enables all * GFM extensions plus wikilinks, underline, and LaTeX math. * * @param input The markdown string or buffer to render * @param theme Optional theme overrides * @returns An ANSI-colored string * * @example * ```ts * const out = Bun.markdown.ansi("# Hello\n\n**bold** and *italic*\n"); * process.stdout.write(out); * * // Plain text, no escape codes * const plain = Bun.markdown.ansi("# Hello", { colors: false }); * * // Enable clickable OSC 8 hyperlinks * const linked = Bun.markdown.ansi("[docs](https://bun.com)", { * hyperlinks: true, * }); * * // Inline images via Kitty Graphics Protocol * const withImg = Bun.markdown.ansi("![alt](./logo.png)", { * kittyGraphics: true, * }); * * // Custom width * const wrapped = Bun.markdown.ansi(longText, { columns: 60 }); * ``` */ export function ansi( input: string | NodeJS.TypedArray | DataView<ArrayBuffer> | ArrayBufferLike, theme?: AnsiTheme, ): string; /** * Render markdown with custom JavaScript callbacks for each element. * * Each callback receives the accumulated children as a string and optional * metadata, and returns a string. Return `null` or `undefined` to omit * an element. If no callback is registered, children pass through unchanged. * * Parser options are passed as a separate third argument. * * @param input The markdown string to render * @param callbacks Callbacks for each element type * @param options Parser options * @returns The accumulated string output * * @example * ```ts * // Custom HTML with classes * const html = Bun.markdown.render("# Title\n\nHello **world**", { * heading: (children, { level }) => `<h${level} class="title">${children}</h${level}>`, * paragraph: (children) => `<p>${children}</p>`, * strong: (children) => `<b>${children}</b>`, * }); * * // ANSI terminal output * const ansi = Bun.markdown.render("# Hello\n\n**bold**", { * he