bun-types 1.3.5-canary.20251209T140747 → 1.3.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -427,8 +427,8 @@ This will allow you to use TailwindCSS utility classes in your HTML and CSS file
427
427
  <!doctype html>
428
428
  <html>
429
429
  <head>
430
- <link rel="stylesheet" href="tailwindcss" />
431
430
  <!-- [!code ++] -->
431
+ <link rel="stylesheet" href="tailwindcss" />
432
432
  </head>
433
433
  <!-- the rest of your HTML... -->
434
434
  </html>
@@ -448,8 +448,8 @@ Alternatively, you can import TailwindCSS in your CSS file:
448
448
  <!doctype html>
449
449
  <html>
450
450
  <head>
451
- <link rel="stylesheet" href="./style.css" />
452
451
  <!-- [!code ++] -->
452
+ <link rel="stylesheet" href="./style.css" />
453
453
  </head>
454
454
  <!-- the rest of your HTML... -->
455
455
  </html>
@@ -1141,6 +1141,84 @@ Remove function calls from a bundle. For example, `--drop=console` will remove a
1141
1141
  </Tab>
1142
1142
  </Tabs>
1143
1143
 
1144
+ ### features
1145
+
1146
+ Enable compile-time feature flags for dead-code elimination. This provides a way to conditionally include or exclude code paths at bundle time using `import { feature } from "bun:bundle"`.
1147
+
1148
+ ```ts title="app.ts" icon="/icons/typescript.svg"
1149
+ import { feature } from "bun:bundle";
1150
+
1151
+ if (feature("PREMIUM")) {
1152
+ // Only included when PREMIUM flag is enabled
1153
+ initPremiumFeatures();
1154
+ }
1155
+
1156
+ if (feature("DEBUG")) {
1157
+ // Only included when DEBUG flag is enabled
1158
+ console.log("Debug mode");
1159
+ }
1160
+ ```
1161
+
1162
+ <Tabs>
1163
+ <Tab title="JavaScript">
1164
+ ```ts title="build.ts" icon="/icons/typescript.svg"
1165
+ await Bun.build({
1166
+ entrypoints: ['./app.ts'],
1167
+ outdir: './out',
1168
+ features: ["PREMIUM"], // PREMIUM=true, DEBUG=false
1169
+ })
1170
+ ```
1171
+ </Tab>
1172
+ <Tab title="CLI">
1173
+ ```bash terminal icon="terminal"
1174
+ bun build ./app.ts --outdir ./out --feature PREMIUM
1175
+ ```
1176
+ </Tab>
1177
+ </Tabs>
1178
+
1179
+ The `feature()` function is replaced with `true` or `false` at bundle time. Combined with minification, unreachable code is eliminated:
1180
+
1181
+ ```ts title="Input" icon="/icons/typescript.svg"
1182
+ import { feature } from "bun:bundle";
1183
+ const mode = feature("PREMIUM") ? "premium" : "free";
1184
+ ```
1185
+
1186
+ ```js title="Output (with --feature PREMIUM --minify)" icon="/icons/javascript.svg"
1187
+ var mode = "premium";
1188
+ ```
1189
+
1190
+ ```js title="Output (without --feature PREMIUM, with --minify)" icon="/icons/javascript.svg"
1191
+ var mode = "free";
1192
+ ```
1193
+
1194
+ **Key behaviors:**
1195
+
1196
+ - `feature()` requires a string literal argument — dynamic values are not supported
1197
+ - The `bun:bundle` import is completely removed from the output
1198
+ - Works with `bun build`, `bun run`, and `bun test`
1199
+ - Multiple flags can be enabled: `--feature FLAG_A --feature FLAG_B`
1200
+ - For type safety, augment the `Registry` interface to restrict `feature()` to known flags (see below)
1201
+
1202
+ **Use cases:**
1203
+
1204
+ - Platform-specific code (`feature("SERVER")` vs `feature("CLIENT")`)
1205
+ - Environment-based features (`feature("DEVELOPMENT")`)
1206
+ - Gradual feature rollouts
1207
+ - A/B testing variants
1208
+ - Paid tier features
1209
+
1210
+ **Type safety:** By default, `feature()` accepts any string. To get autocomplete and catch typos at compile time, create an `env.d.ts` file (or add to an existing `.d.ts`) and augment the `Registry` interface:
1211
+
1212
+ ```ts title="env.d.ts" icon="/icons/typescript.svg"
1213
+ declare module "bun:bundle" {
1214
+ interface Registry {
1215
+ features: "DEBUG" | "PREMIUM" | "BETA_FEATURES";
1216
+ }
1217
+ }
1218
+ ```
1219
+
1220
+ Ensure the file is included in your `tsconfig.json` (e.g., `"include": ["src", "env.d.ts"]`). Now `feature()` only accepts those flags, and invalid strings like `feature("TYPO")` become type errors.
1221
+
1144
1222
  ## Outputs
1145
1223
 
1146
1224
  The `Bun.build` function returns a `Promise<BuildOutput>`, defined as:
@@ -8,7 +8,9 @@ Unlike other npm clients, Bun does not execute arbitrary lifecycle scripts for i
8
8
 
9
9
  <Note>
10
10
  Bun includes a default allowlist of popular packages containing `postinstall` scripts that are known to be safe. You
11
- can see this list [here](https://github.com/oven-sh/bun/blob/main/src/install/default-trusted-dependencies.txt).
11
+ can see this list [here](https://github.com/oven-sh/bun/blob/main/src/install/default-trusted-dependencies.txt). This
12
+ default list only applies to packages installed from npm. For packages from other sources (such as `file:`, `link:`,
13
+ `git:`, or `github:` dependencies), you must explicitly add them to `trustedDependencies`.
12
14
  </Note>
13
15
 
14
16
  ---
@@ -14,16 +14,6 @@ process.on("SIGINT", () => {
14
14
 
15
15
  ---
16
16
 
17
- If you don't know which signal to listen for, you listen to the umbrella `"exit"` event.
18
-
19
- ```ts
20
- process.on("exit", code => {
21
- console.log(`Process exited with code ${code}`);
22
- });
23
- ```
24
-
25
- ---
26
-
27
17
  If you don't know which signal to listen for, you listen to the [`"beforeExit"`](https://nodejs.org/api/process.html#event-beforeexit) and [`"exit"`](https://nodejs.org/api/process.html#event-exit) events.
28
18
 
29
19
  ```ts
@@ -46,6 +46,13 @@ Once added to `trustedDependencies`, install/re-install the package. Bun will re
46
46
 
47
47
  The top 500 npm packages with lifecycle scripts are allowed by default. You can see the full list [here](https://github.com/oven-sh/bun/blob/main/src/install/default-trusted-dependencies.txt).
48
48
 
49
+ <Note>
50
+ The default trusted dependencies list only applies to packages installed from npm. For packages from other sources
51
+ (such as `file:`, `link:`, `git:`, or `github:` dependencies), you must explicitly add them to `trustedDependencies`
52
+ to run their lifecycle scripts, even if the package name matches an entry in the default list. This prevents malicious
53
+ packages from spoofing trusted package names through local file paths or git repositories.
54
+ </Note>
55
+
49
56
  ---
50
57
 
51
58
  ## `--ignore-scripts`
@@ -315,6 +315,109 @@ if (typeof Bun !== "undefined") {
315
315
 
316
316
  ---
317
317
 
318
+ ## Terminal (PTY) support
319
+
320
+ For interactive terminal applications, you can spawn a subprocess with a pseudo-terminal (PTY) attached using the `terminal` option. This makes the subprocess think it's running in a real terminal, enabling features like colored output, cursor movement, and interactive prompts.
321
+
322
+ ```ts
323
+ const proc = Bun.spawn(["bash"], {
324
+ terminal: {
325
+ cols: 80,
326
+ rows: 24,
327
+ data(terminal, data) {
328
+ // Called when data is received from the terminal
329
+ process.stdout.write(data);
330
+ },
331
+ },
332
+ });
333
+
334
+ // Write to the terminal
335
+ proc.terminal.write("echo hello\n");
336
+
337
+ // Wait for the process to exit
338
+ await proc.exited;
339
+
340
+ // Close the terminal
341
+ proc.terminal.close();
342
+ ```
343
+
344
+ When the `terminal` option is provided:
345
+
346
+ - The subprocess sees `process.stdout.isTTY` as `true`
347
+ - `stdin`, `stdout`, and `stderr` are all connected to the terminal
348
+ - `proc.stdin`, `proc.stdout`, and `proc.stderr` return `null` — use the terminal instead
349
+ - Access the terminal via `proc.terminal`
350
+
351
+ ### Terminal options
352
+
353
+ | Option | Description | Default |
354
+ | ------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------ | ------------------ |
355
+ | `cols` | Number of columns | `80` |
356
+ | `rows` | Number of rows | `24` |
357
+ | `name` | Terminal type for PTY configuration (set `TERM` env var separately via `env` option) | `"xterm-256color"` |
358
+ | `data` | Callback when data is received `(terminal, data) => void` | — |
359
+ | `exit` | Callback when PTY stream closes (EOF or error). `exitCode` is PTY lifecycle status (0=EOF, 1=error), not subprocess exit code. Use `proc.exited` for process exit. | — |
360
+ | `drain` | Callback when ready for more data `(terminal) => void` | — |
361
+
362
+ ### Terminal methods
363
+
364
+ The `Terminal` object returned by `proc.terminal` has the following methods:
365
+
366
+ ```ts
367
+ // Write data to the terminal
368
+ proc.terminal.write("echo hello\n");
369
+
370
+ // Resize the terminal
371
+ proc.terminal.resize(120, 40);
372
+
373
+ // Set raw mode (disable line buffering and echo)
374
+ proc.terminal.setRawMode(true);
375
+
376
+ // Keep event loop alive while terminal is open
377
+ proc.terminal.ref();
378
+ proc.terminal.unref();
379
+
380
+ // Close the terminal
381
+ proc.terminal.close();
382
+ ```
383
+
384
+ ### Reusable Terminal
385
+
386
+ You can create a terminal independently and reuse it across multiple subprocesses:
387
+
388
+ ```ts
389
+ await using terminal = new Bun.Terminal({
390
+ cols: 80,
391
+ rows: 24,
392
+ data(term, data) {
393
+ process.stdout.write(data);
394
+ },
395
+ });
396
+
397
+ // Spawn first process
398
+ const proc1 = Bun.spawn(["echo", "first"], { terminal });
399
+ await proc1.exited;
400
+
401
+ // Reuse terminal for another process
402
+ const proc2 = Bun.spawn(["echo", "second"], { terminal });
403
+ await proc2.exited;
404
+
405
+ // Terminal is closed automatically by `await using`
406
+ ```
407
+
408
+ When passing an existing `Terminal` object:
409
+
410
+ - The terminal can be reused across multiple spawns
411
+ - You control when to close the terminal
412
+ - The `exit` callback fires when you call `terminal.close()`, not when each subprocess exits
413
+ - Use `proc.exited` to detect individual subprocess exits
414
+
415
+ This is useful for running multiple commands in sequence through the same terminal session.
416
+
417
+ <Note>Terminal support is only available on POSIX systems (Linux, macOS). It is not available on Windows.</Note>
418
+
419
+ ---
420
+
318
421
  ## Blocking API (`Bun.spawnSync()`)
319
422
 
320
423
  Bun provides a synchronous equivalent of `Bun.spawn` called `Bun.spawnSync`. This is a blocking API that supports the same inputs and parameters as `Bun.spawn`. It returns a `SyncSubprocess` object, which differs from `Subprocess` in a few ways.
@@ -407,6 +510,7 @@ namespace SpawnOptions {
407
510
  timeout?: number;
408
511
  killSignal?: string | number;
409
512
  maxBuffer?: number;
513
+ terminal?: TerminalOptions; // PTY support (POSIX only)
410
514
  }
411
515
 
412
516
  type Readable =
@@ -435,10 +539,11 @@ namespace SpawnOptions {
435
539
  }
436
540
 
437
541
  interface Subprocess extends AsyncDisposable {
438
- readonly stdin: FileSink | number | undefined;
439
- readonly stdout: ReadableStream<Uint8Array> | number | undefined;
440
- readonly stderr: ReadableStream<Uint8Array> | number | undefined;
441
- readonly readable: ReadableStream<Uint8Array> | number | undefined;
542
+ readonly stdin: FileSink | number | undefined | null;
543
+ readonly stdout: ReadableStream<Uint8Array<ArrayBuffer>> | number | undefined | null;
544
+ readonly stderr: ReadableStream<Uint8Array<ArrayBuffer>> | number | undefined | null;
545
+ readonly readable: ReadableStream<Uint8Array<ArrayBuffer>> | number | undefined | null;
546
+ readonly terminal: Terminal | undefined;
442
547
  readonly pid: number;
443
548
  readonly exited: Promise<number>;
444
549
  readonly exitCode: number | null;
@@ -465,6 +570,28 @@ interface SyncSubprocess {
465
570
  pid: number;
466
571
  }
467
572
 
573
+ interface TerminalOptions {
574
+ cols?: number;
575
+ rows?: number;
576
+ name?: string;
577
+ data?: (terminal: Terminal, data: Uint8Array<ArrayBuffer>) => void;
578
+ /** Called when PTY stream closes (EOF or error). exitCode is PTY lifecycle status (0=EOF, 1=error), not subprocess exit code. */
579
+ exit?: (terminal: Terminal, exitCode: number, signal: string | null) => void;
580
+ drain?: (terminal: Terminal) => void;
581
+ }
582
+
583
+ interface Terminal extends AsyncDisposable {
584
+ readonly stdin: number;
585
+ readonly stdout: number;
586
+ readonly closed: boolean;
587
+ write(data: string | BufferSource): number;
588
+ resize(cols: number, rows: number): void;
589
+ setRawMode(enabled: boolean): void;
590
+ ref(): void;
591
+ unref(): void;
592
+ close(): void;
593
+ }
594
+
468
595
  interface ResourceUsage {
469
596
  contextSwitches: {
470
597
  voluntary: number;
package/globals.d.ts CHANGED
@@ -1,9 +1,12 @@
1
1
  declare module "bun" {
2
2
  namespace __internal {
3
- type NodeCryptoWebcryptoSubtleCrypto = import("crypto").webcrypto.SubtleCrypto;
4
3
  type NodeCryptoWebcryptoCryptoKey = import("crypto").webcrypto.CryptoKey;
5
4
  type NodeCryptoWebcryptoCryptoKeyPair = import("crypto").webcrypto.CryptoKeyPair;
6
5
 
6
+ type LibEmptyOrNodeCryptoWebcryptoSubtleCrypto = LibDomIsLoaded extends true
7
+ ? {}
8
+ : import("crypto").webcrypto.SubtleCrypto;
9
+
7
10
  type LibWorkerOrBunWorker = LibDomIsLoaded extends true ? {} : Bun.Worker;
8
11
  type LibEmptyOrBunWebSocket = LibDomIsLoaded extends true ? {} : Bun.WebSocket;
9
12
 
@@ -14,7 +17,9 @@ declare module "bun" {
14
17
  ? {}
15
18
  : import("node:stream/web").DecompressionStream;
16
19
 
17
- type LibPerformanceOrNodePerfHooksPerformance = LibDomIsLoaded extends true ? {} : import("perf_hooks").Performance;
20
+ type LibPerformanceOrNodePerfHooksPerformance = LibDomIsLoaded extends true
21
+ ? {}
22
+ : import("node:perf_hooks").Performance;
18
23
  type LibEmptyOrPerformanceEntry = LibDomIsLoaded extends true ? {} : import("node:perf_hooks").PerformanceEntry;
19
24
  type LibEmptyOrPerformanceMark = LibDomIsLoaded extends true ? {} : import("node:perf_hooks").PerformanceMark;
20
25
  type LibEmptyOrPerformanceMeasure = LibDomIsLoaded extends true ? {} : import("node:perf_hooks").PerformanceMeasure;
@@ -83,6 +88,24 @@ declare var WritableStream: Bun.__internal.UseLibDomIfAvailable<
83
88
  }
84
89
  >;
85
90
 
91
+ interface CompressionStream extends Bun.__internal.LibEmptyOrNodeStreamWebCompressionStream {}
92
+ declare var CompressionStream: Bun.__internal.UseLibDomIfAvailable<
93
+ "CompressionStream",
94
+ {
95
+ prototype: CompressionStream;
96
+ new (format: Bun.CompressionFormat): CompressionStream;
97
+ }
98
+ >;
99
+
100
+ interface DecompressionStream extends Bun.__internal.LibEmptyOrNodeStreamWebDecompressionStream {}
101
+ declare var DecompressionStream: Bun.__internal.UseLibDomIfAvailable<
102
+ "DecompressionStream",
103
+ {
104
+ prototype: DecompressionStream;
105
+ new (format: Bun.CompressionFormat): DecompressionStream;
106
+ }
107
+ >;
108
+
86
109
  interface Worker extends Bun.__internal.LibWorkerOrBunWorker {}
87
110
  declare var Worker: Bun.__internal.UseLibDomIfAvailable<
88
111
  "Worker",
@@ -206,7 +229,7 @@ interface TextEncoder extends Bun.__internal.LibEmptyOrNodeUtilTextEncoder {
206
229
  * @param src The text to encode.
207
230
  * @param dest The array to hold the encode result.
208
231
  */
209
- encodeInto(src?: string, dest?: Bun.BufferSource): import("util").EncodeIntoResult;
232
+ encodeInto(src?: string, dest?: Bun.BufferSource): import("node:util").TextEncoderEncodeIntoResult;
210
233
  }
211
234
  declare var TextEncoder: Bun.__internal.UseLibDomIfAvailable<
212
235
  "TextEncoder",
@@ -278,30 +301,6 @@ declare var Event: {
278
301
  new (type: string, eventInitDict?: Bun.EventInit): Event;
279
302
  };
280
303
 
281
- /**
282
- * Unimplemented in Bun
283
- */
284
- interface CompressionStream extends Bun.__internal.LibEmptyOrNodeStreamWebCompressionStream {}
285
- /**
286
- * Unimplemented in Bun
287
- */
288
- declare var CompressionStream: Bun.__internal.UseLibDomIfAvailable<
289
- "CompressionStream",
290
- typeof import("node:stream/web").CompressionStream
291
- >;
292
-
293
- /**
294
- * Unimplemented in Bun
295
- */
296
- interface DecompressionStream extends Bun.__internal.LibEmptyOrNodeStreamWebCompressionStream {}
297
- /**
298
- * Unimplemented in Bun
299
- */
300
- declare var DecompressionStream: Bun.__internal.UseLibDomIfAvailable<
301
- "DecompressionStream",
302
- typeof import("node:stream/web").DecompressionStream
303
- >;
304
-
305
304
  interface EventTarget {
306
305
  /**
307
306
  * Adds a new handler for the `type` event. Any given `listener` is added only once per `type` and per `capture` option value.
@@ -958,7 +957,7 @@ declare function alert(message?: string): void;
958
957
  declare function confirm(message?: string): boolean;
959
958
  declare function prompt(message?: string, _default?: string): string | null;
960
959
 
961
- interface SubtleCrypto extends Bun.__internal.NodeCryptoWebcryptoSubtleCrypto {}
960
+ interface SubtleCrypto extends Bun.__internal.LibEmptyOrNodeCryptoWebcryptoSubtleCrypto {}
962
961
  declare var SubtleCrypto: {
963
962
  prototype: SubtleCrypto;
964
963
  new (): SubtleCrypto;
@@ -1694,6 +1693,10 @@ declare var EventSource: Bun.__internal.UseLibDomIfAvailable<
1694
1693
 
1695
1694
  interface Performance extends Bun.__internal.LibPerformanceOrNodePerfHooksPerformance {}
1696
1695
  declare var performance: Bun.__internal.UseLibDomIfAvailable<"performance", Performance>;
1696
+ declare var Performance: Bun.__internal.UseLibDomIfAvailable<
1697
+ "Performance",
1698
+ { new (): Performance; prototype: Performance }
1699
+ >;
1697
1700
 
1698
1701
  interface PerformanceEntry extends Bun.__internal.LibEmptyOrPerformanceEntry {}
1699
1702
  declare var PerformanceEntry: Bun.__internal.UseLibDomIfAvailable<
package/index.d.ts CHANGED
@@ -23,6 +23,7 @@
23
23
  /// <reference path="./serve.d.ts" />
24
24
  /// <reference path="./sql.d.ts" />
25
25
  /// <reference path="./security.d.ts" />
26
+ /// <reference path="./bundle.d.ts" />
26
27
 
27
28
  /// <reference path="./bun.ns.d.ts" />
28
29
 
package/overrides.d.ts CHANGED
@@ -86,7 +86,7 @@ declare global {
86
86
  reallyExit(code?: number): never;
87
87
  dlopen(module: { exports: any }, filename: string, flags?: number): void;
88
88
  _exiting: boolean;
89
- noDeprecation: boolean;
89
+ noDeprecation?: boolean | undefined;
90
90
 
91
91
  binding(m: "constants"): {
92
92
  os: typeof import("node:os").constants;
@@ -308,11 +308,11 @@ declare global {
308
308
  }
309
309
  }
310
310
 
311
- declare module "fs/promises" {
311
+ declare module "node:fs/promises" {
312
312
  function exists(path: Bun.PathLike): Promise<boolean>;
313
313
  }
314
314
 
315
- declare module "tls" {
315
+ declare module "node:tls" {
316
316
  interface BunConnectionOptions extends Omit<ConnectionOptions, "key" | "ca" | "tls" | "cert"> {
317
317
  /**
318
318
  * Optionally override the trusted CA certificates. Default is to trust
@@ -359,3 +359,18 @@ declare module "tls" {
359
359
 
360
360
  function connect(options: BunConnectionOptions, secureConnectListener?: () => void): TLSSocket;
361
361
  }
362
+
363
+ declare module "console" {
364
+ interface Console {
365
+ /**
366
+ * Asynchronously read lines from standard input (fd 0)
367
+ *
368
+ * ```ts
369
+ * for await (const line of console) {
370
+ * console.log(line);
371
+ * }
372
+ * ```
373
+ */
374
+ [Symbol.asyncIterator](): AsyncIterableIterator<string>;
375
+ }
376
+ }
package/package.json CHANGED
@@ -33,5 +33,5 @@
33
33
  "bun.js",
34
34
  "types"
35
35
  ],
36
- "version": "1.3.5-canary.20251209T140747"
36
+ "version": "1.3.5"
37
37
  }
package/test.d.ts CHANGED
@@ -428,6 +428,8 @@ declare module "bun:test" {
428
428
  }
429
429
 
430
430
  namespace __internal {
431
+ type IfNeverThenElse<T, Else> = [T] extends [never] ? Else : T;
432
+
431
433
  type IsTuple<T> = T extends readonly unknown[]
432
434
  ? number extends T["length"]
433
435
  ? false // It's an array with unknown length, not a tuple
@@ -1097,8 +1099,8 @@ declare module "bun:test" {
1097
1099
  *
1098
1100
  * @param expected the expected value
1099
1101
  */
1100
- toContainKey(expected: keyof T): void;
1101
- toContainKey<X = T>(expected: NoInfer<keyof X>): void;
1102
+ toContainKey(expected: __internal.IfNeverThenElse<keyof T, PropertyKey>): void;
1103
+ toContainKey<X = T>(expected: __internal.IfNeverThenElse<NoInfer<keyof X>, PropertyKey>): void;
1102
1104
 
1103
1105
  /**
1104
1106
  * Asserts that an `object` contains all the provided keys.
@@ -1114,8 +1116,8 @@ declare module "bun:test" {
1114
1116
  *
1115
1117
  * @param expected the expected value
1116
1118
  */
1117
- toContainAllKeys(expected: Array<keyof T>): void;
1118
- toContainAllKeys<X = T>(expected: NoInfer<Array<keyof X>>): void;
1119
+ toContainAllKeys(expected: Array<__internal.IfNeverThenElse<keyof T, PropertyKey>>): void;
1120
+ toContainAllKeys<X = T>(expected: Array<__internal.IfNeverThenElse<NoInfer<keyof X>, PropertyKey>>): void;
1119
1121
 
1120
1122
  /**
1121
1123
  * Asserts that an `object` contains at least one of the provided keys.
@@ -1131,8 +1133,8 @@ declare module "bun:test" {
1131
1133
  *
1132
1134
  * @param expected the expected value
1133
1135
  */
1134
- toContainAnyKeys(expected: Array<keyof T>): void;
1135
- toContainAnyKeys<X = T>(expected: NoInfer<Array<keyof X>>): void;
1136
+ toContainAnyKeys(expected: Array<__internal.IfNeverThenElse<keyof T, PropertyKey>>): void;
1137
+ toContainAnyKeys<X = T>(expected: Array<__internal.IfNeverThenElse<NoInfer<keyof X>, PropertyKey>>): void;
1136
1138
 
1137
1139
  /**
1138
1140
  * Asserts that an `object` contain the provided value.
@@ -1224,8 +1226,8 @@ declare module "bun:test" {
1224
1226
  *
1225
1227
  * @param expected the expected value
1226
1228
  */
1227
- toContainKeys(expected: Array<keyof T>): void;
1228
- toContainKeys<X = T>(expected: NoInfer<Array<keyof X>>): void;
1229
+ toContainKeys(expected: Array<__internal.IfNeverThenElse<keyof T, PropertyKey>>): void;
1230
+ toContainKeys<X = T>(expected: Array<__internal.IfNeverThenElse<NoInfer<keyof X>, PropertyKey>>): void;
1229
1231
 
1230
1232
  /**
1231
1233
  * Asserts that a value contains and equals what is expected.