From 65ccb39778d4ae1cca22996512ef9f79eb2d058c Mon Sep 17 00:00:00 2001 From: Alistair Smith Date: Thu, 10 Jul 2025 22:47:42 -0700 Subject: [PATCH] Convert bun-types.test.ts to TS compiler api, fix forward-declared empty interfaces (#20960) --- packages/bun-types/globals.d.ts | 59 ++- test/bun.lock | 4 +- test/integration/bun-types/bun-types.test.ts | 426 ++++++++++++++---- .../bun-types/fixture/utilities.ts | 2 + test/package.json | 2 +- 5 files changed, 381 insertions(+), 112 deletions(-) diff --git a/packages/bun-types/globals.d.ts b/packages/bun-types/globals.d.ts index 567606d956..e22a792449 100644 --- a/packages/bun-types/globals.d.ts +++ b/packages/bun-types/globals.d.ts @@ -1,19 +1,26 @@ declare module "bun" { namespace __internal { - type NodeWorkerThreadsWorker = import("node:worker_threads").Worker; - type LibWorkerOrBunWorker = Bun.__internal.UseLibDomIfAvailable<"Worker", Bun.Worker>; - - type LibPerformanceOrNodePerfHooksPerformance = Bun.__internal.UseLibDomIfAvailable< - "Performance", - import("perf_hooks").Performance - >; - type NodeCryptoWebcryptoSubtleCrypto = import("crypto").webcrypto.SubtleCrypto; type NodeCryptoWebcryptoCryptoKey = import("crypto").webcrypto.CryptoKey; type NodeCryptoWebcryptoCryptoKeyPair = import("crypto").webcrypto.CryptoKeyPair; + type LibWorkerOrBunWorker = LibDomIsLoaded extends true ? {} : Bun.Worker; type LibEmptyOrBunWebSocket = LibDomIsLoaded extends true ? {} : Bun.WebSocket; + type LibPerformanceOrNodePerfHooksPerformance = LibDomIsLoaded extends true ? {} : import("perf_hooks").Performance; + type LibEmptyOrPerformanceEntry = LibDomIsLoaded extends true ? {} : import("node:perf_hooks").PerformanceEntry; + type LibEmptyOrPerformanceMark = LibDomIsLoaded extends true ? {} : import("node:perf_hooks").PerformanceMark; + type LibEmptyOrPerformanceMeasure = LibDomIsLoaded extends true ? {} : import("node:perf_hooks").PerformanceMeasure; + type LibEmptyOrPerformanceObserver = LibDomIsLoaded extends true + ? {} + : import("node:perf_hooks").PerformanceObserver; + type LibEmptyOrPerformanceObserverEntryList = LibDomIsLoaded extends true + ? {} + : import("node:perf_hooks").PerformanceObserverEntryList; + type LibEmptyOrPerformanceResourceTiming = LibDomIsLoaded extends true + ? {} + : import("node:perf_hooks").PerformanceResourceTiming; + type LibEmptyOrNodeUtilTextEncoder = LibDomIsLoaded extends true ? {} : import("node:util").TextEncoder; type LibEmptyOrNodeStreamWebTextEncoderStream = LibDomIsLoaded extends true ? {} @@ -33,6 +40,20 @@ declare module "bun" { : import("node:stream/web").WritableStream; type LibEmptyOrNodeMessagePort = LibDomIsLoaded extends true ? {} : import("node:worker_threads").MessagePort; + type LibEmptyOrBroadcastChannel = LibDomIsLoaded extends true ? {} : import("node:worker_threads").BroadcastChannel; + type LibEmptyOrEventSource = LibDomIsLoaded extends true ? {} : import("undici-types").EventSource; + + type LibEmptyOrReadableByteStreamController = LibDomIsLoaded extends true + ? {} + : import("node:stream/web").ReadableByteStreamController; + + type ReadableStreamBYOBReader = LibDomIsLoaded extends true + ? {} + : import("node:stream/web").ReadableStreamBYOBReader; + + type ReadableStreamBYOBRequest = LibDomIsLoaded extends true + ? {} + : import("node:stream/web").ReadableStreamBYOBRequest; } } @@ -1495,7 +1516,7 @@ interface Uint8ArrayConstructor { fromHex(hex: string): Uint8Array; } -interface BroadcastChannel {} +interface BroadcastChannel extends Bun.__internal.LibEmptyOrBroadcastChannel {} declare var BroadcastChannel: Bun.__internal.UseLibDomIfAvailable< "BroadcastChannel", typeof import("node:worker_threads").BroadcastChannel @@ -1599,7 +1620,7 @@ interface FormData { } declare var FormData: Bun.__internal.UseLibDomIfAvailable<"FormData", { prototype: FormData; new (): FormData }>; -interface EventSource {} +interface EventSource extends Bun.__internal.LibEmptyOrEventSource {} declare var EventSource: Bun.__internal.UseLibDomIfAvailable< "EventSource", { prototype: EventSource; new (): EventSource } @@ -1608,55 +1629,55 @@ declare var EventSource: Bun.__internal.UseLibDomIfAvailable< interface Performance extends Bun.__internal.LibPerformanceOrNodePerfHooksPerformance {} declare var performance: Bun.__internal.UseLibDomIfAvailable<"performance", Performance>; -interface PerformanceEntry {} +interface PerformanceEntry extends Bun.__internal.LibEmptyOrPerformanceEntry {} declare var PerformanceEntry: Bun.__internal.UseLibDomIfAvailable< "PerformanceEntry", { prototype: PerformanceEntry; new (): PerformanceEntry } >; -interface PerformanceMark {} +interface PerformanceMark extends Bun.__internal.LibEmptyOrPerformanceMark {} declare var PerformanceMark: Bun.__internal.UseLibDomIfAvailable< "PerformanceMark", { prototype: PerformanceMark; new (): PerformanceMark } >; -interface PerformanceMeasure {} +interface PerformanceMeasure extends Bun.__internal.LibEmptyOrPerformanceMeasure {} declare var PerformanceMeasure: Bun.__internal.UseLibDomIfAvailable< "PerformanceMeasure", { prototype: PerformanceMeasure; new (): PerformanceMeasure } >; -interface PerformanceObserver {} +interface PerformanceObserver extends Bun.__internal.LibEmptyOrPerformanceObserver {} declare var PerformanceObserver: Bun.__internal.UseLibDomIfAvailable< "PerformanceObserver", { prototype: PerformanceObserver; new (): PerformanceObserver } >; -interface PerformanceObserverEntryList {} +interface PerformanceObserverEntryList extends Bun.__internal.LibEmptyOrPerformanceObserverEntryList {} declare var PerformanceObserverEntryList: Bun.__internal.UseLibDomIfAvailable< "PerformanceObserverEntryList", { prototype: PerformanceObserverEntryList; new (): PerformanceObserverEntryList } >; -interface PerformanceResourceTiming {} +interface PerformanceResourceTiming extends Bun.__internal.LibEmptyOrPerformanceResourceTiming {} declare var PerformanceResourceTiming: Bun.__internal.UseLibDomIfAvailable< "PerformanceResourceTiming", { prototype: PerformanceResourceTiming; new (): PerformanceResourceTiming } >; -interface ReadableByteStreamController {} +interface ReadableByteStreamController extends Bun.__internal.LibEmptyOrReadableByteStreamController {} declare var ReadableByteStreamController: Bun.__internal.UseLibDomIfAvailable< "ReadableByteStreamController", { prototype: ReadableByteStreamController; new (): ReadableByteStreamController } >; -interface ReadableStreamBYOBReader {} +interface ReadableStreamBYOBReader extends Bun.__internal.LibEmptyOrReadableByteStreamController {} declare var ReadableStreamBYOBReader: Bun.__internal.UseLibDomIfAvailable< "ReadableStreamBYOBReader", { prototype: ReadableStreamBYOBReader; new (): ReadableStreamBYOBReader } >; -interface ReadableStreamBYOBRequest {} +interface ReadableStreamBYOBRequest extends Bun.__internal.LibEmptyOrReadableByteStreamController {} declare var ReadableStreamBYOBRequest: Bun.__internal.UseLibDomIfAvailable< "ReadableStreamBYOBRequest", { prototype: ReadableStreamBYOBRequest; new (): ReadableStreamBYOBRequest } diff --git a/test/bun.lock b/test/bun.lock index fb4796cfb1..970dedfbc5 100644 --- a/test/bun.lock +++ b/test/bun.lock @@ -82,7 +82,7 @@ "tsyringe": "4.8.0", "type-graphql": "2.0.0-rc.2", "typeorm": "0.3.20", - "typescript": "5.0.2", + "typescript": "^5.8.3", "undici": "5.20.0", "unzipper": "0.12.3", "uuid": "11.1.0", @@ -2476,7 +2476,7 @@ "typeorm": ["typeorm@0.3.20", "", { "dependencies": { "@sqltools/formatter": "^1.2.5", "app-root-path": "^3.1.0", "buffer": "^6.0.3", "chalk": "^4.1.2", "cli-highlight": "^2.1.11", "dayjs": "^1.11.9", "debug": "^4.3.4", "dotenv": "^16.0.3", "glob": "^10.3.10", "mkdirp": "^2.1.3", "reflect-metadata": "^0.2.1", "sha.js": "^2.4.11", "tslib": "^2.5.0", "uuid": "^9.0.0", "yargs": "^17.6.2" }, "peerDependencies": { "@google-cloud/spanner": "^5.18.0", "@sap/hana-client": "^2.12.25", "better-sqlite3": "^7.1.2 || ^8.0.0 || ^9.0.0", "hdb-pool": "^0.1.6", "ioredis": "^5.0.4", "mongodb": "^5.8.0", "mssql": "^9.1.1 || ^10.0.1", "mysql2": "^2.2.5 || ^3.0.1", "oracledb": "^6.3.0", "pg": "^8.5.1", "pg-native": "^3.0.0", "pg-query-stream": "^4.0.0", "redis": "^3.1.1 || ^4.0.0", "sql.js": "^1.4.0", "sqlite3": "^5.0.3", "ts-node": "^10.7.0", "typeorm-aurora-data-api-driver": "^2.0.0" }, "optionalPeers": ["@google-cloud/spanner", "@sap/hana-client", "better-sqlite3", "hdb-pool", "ioredis", "mongodb", "mssql", "mysql2", "oracledb", "pg", "pg-native", "pg-query-stream", "redis", "sql.js", "sqlite3", "ts-node", "typeorm-aurora-data-api-driver"], "bin": { "typeorm": "cli.js", "typeorm-ts-node-esm": "cli-ts-node-esm.js", "typeorm-ts-node-commonjs": "cli-ts-node-commonjs.js" } }, "sha512-sJ0T08dV5eoZroaq9uPKBoNcGslHBR4E4y+EBHs//SiGbblGe7IeduP/IH4ddCcj0qp3PHwDwGnuvqEAnKlq/Q=="], - "typescript": ["typescript@5.0.2", "", { "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" } }, "sha512-wVORMBGO/FAs/++blGNeAVdbNKtIh1rbBL2EyQ1+J9lClJ93KiiKe8PmFIVdXhHcyv44SL9oglmfeSsndo0jRw=="], + "typescript": ["typescript@5.8.3", "", { "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" } }, "sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ=="], "ufo": ["ufo@1.5.4", "", {}, "sha512-UsUk3byDzKd04EyoZ7U4DOlxQaD14JUKQl6/P7wiX4FNvUfm3XL246n9W5AmqwW5RSFJ27NAuM0iLscAOYUiGQ=="], diff --git a/test/integration/bun-types/bun-types.test.ts b/test/integration/bun-types/bun-types.test.ts index d8e355a007..44ff44c029 100644 --- a/test/integration/bun-types/bun-types.test.ts +++ b/test/integration/bun-types/bun-types.test.ts @@ -1,8 +1,11 @@ import { fileURLToPath, $ as Shell } from "bun"; -import { afterAll, beforeAll, beforeEach, describe, expect, test } from "bun:test"; +import { afterAll, beforeAll, describe, expect, test } from "bun:test"; +import { existsSync, readFileSync } from "node:fs"; import { cp, mkdtemp, rm } from "node:fs/promises"; import { tmpdir } from "node:os"; -import { join } from "node:path"; +import { dirname, join, relative } from "node:path"; + +import ts from "typescript"; const BUN_REPO_ROOT = fileURLToPath(import.meta.resolve("../../../")); const BUN_TYPES_PACKAGE_ROOT = join(BUN_REPO_ROOT, "packages", "bun-types"); @@ -12,7 +15,15 @@ const BUN_TYPES_PACKAGE_JSON_PATH = join(BUN_TYPES_PACKAGE_ROOT, "package.json") const BUN_VERSION = (process.env.BUN_VERSION ?? Bun.version ?? process.versions.bun).replace(/^.*v/, ""); const BUN_TYPES_TARBALL_NAME = `types-bun-${BUN_VERSION}.tgz`; -const $ = Shell.cwd(BUN_REPO_ROOT).nothrow(); +const { config: sourceTsconfig } = ts.readConfigFile(TSCONFIG_SOURCE_PATH, ts.sys.readFile); + +const DEFAULT_COMPILER_OPTIONS = ts.parseJsonConfigFileContent( + sourceTsconfig, + ts.sys, + dirname(TSCONFIG_SOURCE_PATH), +).options; + +const $ = Shell.cwd(BUN_REPO_ROOT); let TEMP_DIR: string; let FIXTURE_DIR: string; @@ -32,7 +43,7 @@ beforeAll(async () => { # temp package.json with @types/bun name and version cp package.json package.json.backup - `; + `.quiet(); const pkg = await Bun.file(BUN_TYPES_PACKAGE_JSON_PATH).json(); @@ -52,7 +63,7 @@ beforeAll(async () => { bun uninstall @types/bun || true bun add @types/bun@${BUN_TYPES_TARBALL_NAME} rm ${BUN_TYPES_TARBALL_NAME} - `; + `.quiet(); } catch (e) { if (e instanceof Bun.$.ShellError) { console.log(e.stderr.toString()); @@ -62,17 +73,130 @@ beforeAll(async () => { } }); -beforeEach(async () => { - await $` - cd ${FIXTURE_DIR} - cp ${TSCONFIG_SOURCE_PATH} tsconfig.json - sed -i 's/"skipLibCheck": true/"skipLibCheck": false/' tsconfig.json - cat tsconfig.json - `; -}); +async function diagnose(fixtureDir: string, tsconfig: Partial) { + const glob = new Bun.Glob("**/*.{ts,tsx}").scan({ + cwd: fixtureDir, + absolute: true, + }); + + const files = (await Array.fromAsync(glob)).filter(file => !file.includes("node_modules")); + + const options: ts.CompilerOptions = { + ...DEFAULT_COMPILER_OPTIONS, + ...tsconfig, + + // always check lib files for this integration test + // (prevent https://github.com/oven-sh/bun/issues/8761 ever happening again) + skipLibCheck: false, + }; + + const host: ts.LanguageServiceHost = { + getScriptFileNames: () => files, + getScriptVersion: () => "0", + getScriptSnapshot: fileName => { + if (!existsSync(fileName)) { + return undefined; + } + + return ts.ScriptSnapshot.fromString(readFileSync(fileName).toString()); + }, + getCurrentDirectory: () => fixtureDir, + getCompilationSettings: () => options, + getDefaultLibFileName: options => ts.getDefaultLibFilePath(options), + fileExists: ts.sys.fileExists, + readFile: ts.sys.readFile, + readDirectory: ts.sys.readDirectory, + }; + + const service = ts.createLanguageService(host, ts.createDocumentRegistry(true, fixtureDir)); + + const program = service.getProgram(); + if (!program) throw new Error("Failed to create program"); + + const diagnostics = ts + .getPreEmitDiagnostics(program) + .concat(program.getOptionsDiagnostics()) + .concat(program.getSyntacticDiagnostics()) + .concat(program.getConfigFileParsingDiagnostics()) + .concat(program.getDeclarationDiagnostics()) + .concat(program.emit().diagnostics) + .map(diagnostic => ({ + category: ts.DiagnosticCategory[diagnostic.category], + file: diagnostic.file?.fileName ? relative(fixtureDir, diagnostic.file?.fileName) : null, + message: typeof diagnostic.messageText === "string" ? diagnostic.messageText : diagnostic.messageText.messageText, + code: diagnostic.code, + })); + + return { + diagnostics, + emptyInterfaces: checkForEmptyInterfaces(program, fixtureDir), + }; +} + +function checkForEmptyInterfaces(program: ts.Program, fixtureDir: string) { + const empties = new Set(); + + const checker = program.getTypeChecker(); + + const anySourceFile = program.getSourceFiles()[0]; + if (!anySourceFile) { + return empties; + } + + const globalSymbols = checker.getSymbolsInScope(anySourceFile, ts.SymbolFlags.Interface); + + for (const symbol of globalSymbols) { + // find only globals + const declarations = symbol.declarations || []; + + const concernsBun = declarations.some(decl => decl.getSourceFile().fileName.includes("node_modules/@types/bun")); + + if (!concernsBun) { + // the lion is not concerned by symbols outside of bun + continue; + } + + const isGlobal = declarations.some(decl => { + const sourceFile = decl.getSourceFile(); + let parent = decl.parent; + + while (parent && parent !== sourceFile) { + if (ts.isModuleDeclaration(parent) || ts.isModuleBlock(parent)) { + return false; + } + parent = parent.parent; + } + + return true; + }); + + if (!isGlobal) { + continue; + } + + const symbolType = checker.getDeclaredTypeOfSymbol(symbol); + const properties = checker.getPropertiesOfType(symbolType); + const callSignatures = checker.getSignaturesOfType(symbolType, ts.SignatureKind.Call); + const constructSignatures = checker.getSignaturesOfType(symbolType, ts.SignatureKind.Construct); + const indexInfos = checker.getIndexInfosOfType(symbolType); + + if ( + properties.length === 0 && + callSignatures.length === 0 && + constructSignatures.length === 0 && + indexInfos.length === 0 + ) { + empties.add(symbol.name); + } + } + + return empties; +} afterAll(async () => { if (TEMP_DIR) { + console.log(TEMP_DIR); + if (Bun.env.TYPES_INTEGRATION_TEST_KEEP_TEMP_DIR === "true") { console.log(`Keeping temp dir ${TEMP_DIR} for debugging`); } else { @@ -83,87 +207,209 @@ afterAll(async () => { describe("@types/bun integration test", () => { test("checks without lib.dom.d.ts", async () => { - const p = await $` - cd ${FIXTURE_DIR} - bun run check - `; + const { diagnostics, emptyInterfaces } = await diagnose(FIXTURE_DIR, {}); - expect(p.exitCode).toBe(0); + expect(emptyInterfaces).toEqual(new Set()); + expect(diagnostics).toEqual([]); }); test("checks with lib.dom.d.ts", async () => { - const tsconfig = Bun.file(join(FIXTURE_DIR, "tsconfig.json")); - await tsconfig.write( - (await tsconfig.text()).replace( - /"lib": \["ESNext"\]/, - '"lib": ["ESNext", "DOM", "DOM.Iterable", "DOM.AsyncIterable"]', - ), - ); + const { diagnostics, emptyInterfaces } = await diagnose(FIXTURE_DIR, { + lib: ["ESNext", "DOM", "DOM.Iterable", "DOM.AsyncIterable"].map(name => `lib.${name.toLowerCase()}.d.ts`), + }); - const p = await $` - cd ${FIXTURE_DIR} - bun run check - `; - - const importantLines = [ - "globals.ts", - "error TS2353: Object literal may only specify known properties, and 'headers' does not exist in type 'string[]'.", - - "http.ts", - `error TS2345: Argument of type '() => AsyncGenerator | "hey", void, unknown>' is not assignable to parameter of type 'BodyInit | null | undefined'.`, - `error TS2345: Argument of type 'AsyncGenerator | "it works!", void, unknown>' is not assignable to parameter of type 'BodyInit | null | undefined'`, - `Type 'AsyncGenerator | "it works!", void, unknown>' is missing the following properties from type 'ReadableStream'`, - - "index.ts", - "error TS2345: Argument of type 'AsyncGenerator, void, unknown>' is not assignable to parameter of type 'BodyInit | null | undefined'.", - "error TS2345: Argument of type '{ headers: { \"x-bun\": string; }; }' is not assignable to parameter of type 'number'.", - - "streams.ts", - "error TS2769: No overload matches this call.", - "ReadableStream>', gave the following error.", - "Overload 1 of 3, '(underlyingSource: UnderlyingByteSource, strategy?: { highWaterMark?: number", // This line truncates because we've seen TypeScript emit differing messages in different environments - `Type '"direct"' is not assignable to type '"bytes"'`, - "error TS2339: Property 'write' does not exist on type 'ReadableByteStreamController'.", - "error TS2339: Property 'json' does not exist on type 'ReadableStream>'.", - "error TS2339: Property 'bytes' does not exist on type 'ReadableStream>'.", - "error TS2339: Property 'text' does not exist on type 'ReadableStream>'.", - "error TS2339: Property 'blob' does not exist on type 'ReadableStream>'.", - - "websocket.ts", - `error TS2353: Object literal may only specify known properties, and 'protocols' does not exist in type 'string[]'.`, - `error TS2353: Object literal may only specify known properties, and 'protocol' does not exist in type 'string[]'.`, - `error TS2353: Object literal may only specify known properties, and 'protocol' does not exist in type 'string[]'.`, - `error TS2353: Object literal may only specify known properties, and 'headers' does not exist in type 'string[]'.`, - `error TS2353: Object literal may only specify known properties, and 'protocols' does not exist in type 'string[]'.`, - `error TS2554: Expected 2 arguments, but got 0.`, - `error TS2551: Property 'URL' does not exist on type 'WebSocket'. Did you mean 'url'?`, - `error TS2322: Type '"nodebuffer"' is not assignable to type 'BinaryType'.`, - `error TS2339: Property 'ping' does not exist on type 'WebSocket'.`, - `error TS2339: Property 'ping' does not exist on type 'WebSocket'.`, - `error TS2339: Property 'ping' does not exist on type 'WebSocket'.`, - `error TS2339: Property 'ping' does not exist on type 'WebSocket'.`, - `error TS2339: Property 'pong' does not exist on type 'WebSocket'.`, - `error TS2339: Property 'pong' does not exist on type 'WebSocket'.`, - `error TS2339: Property 'pong' does not exist on type 'WebSocket'.`, - `error TS2339: Property 'pong' does not exist on type 'WebSocket'.`, - `error TS2339: Property 'terminate' does not exist on type 'WebSocket'.`, - - "worker.ts", - "error TS2339: Property 'ref' does not exist on type 'Worker'.", - "error TS2339: Property 'unref' does not exist on type 'Worker'.", - "error TS2339: Property 'threadId' does not exist on type 'Worker'.", - ]; - - const fullOutput = p.stdout.toString() + p.stderr.toString(); - - for (const line of importantLines) { - expect(fullOutput).toContain(line); - } - - const expectedErrorCount = importantLines.join("\n").match(/error/g)?.length ?? 0; - const actualErrorCount = fullOutput.match(/error/g)?.length ?? 0; - expect(actualErrorCount).toBe(expectedErrorCount); - - expect(p.exitCode).toBe(2); + expect(emptyInterfaces).toEqual(new Set()); + expect(diagnostics).toEqual([ + { + category: "Error", + file: "globals.ts", + message: "Object literal may only specify known properties, and 'headers' does not exist in type 'string[]'.", + code: 2353, + }, + { + category: "Error", + file: "http.ts", + message: + "Argument of type '() => AsyncGenerator | \"hey\", void, unknown>' is not assignable to parameter of type 'BodyInit | null | undefined'.", + code: 2345, + }, + { + category: "Error", + file: "http.ts", + message: + "Argument of type 'AsyncGenerator | \"it works!\", void, unknown>' is not assignable to parameter of type 'BodyInit | null | undefined'.", + code: 2345, + }, + { + category: "Error", + file: "index.ts", + message: + "Argument of type 'AsyncGenerator, void, unknown>' is not assignable to parameter of type 'BodyInit | null | undefined'.", + code: 2345, + }, + { + category: "Error", + file: "index.ts", + message: + "Argument of type '{ headers: { \"x-bun\": string; }; }' is not assignable to parameter of type 'number'.", + code: 2345, + }, + { + category: "Error", + file: "streams.ts", + message: "No overload matches this call.", + code: 2769, + }, + { + category: "Error", + file: "streams.ts", + message: "Property 'write' does not exist on type 'ReadableByteStreamController'.", + code: 2339, + }, + { + category: "Error", + file: "streams.ts", + message: "Property 'json' does not exist on type 'ReadableStream>'.", + code: 2339, + }, + { + category: "Error", + file: "streams.ts", + message: "Property 'bytes' does not exist on type 'ReadableStream>'.", + code: 2339, + }, + { + category: "Error", + file: "streams.ts", + message: "Property 'text' does not exist on type 'ReadableStream>'.", + code: 2339, + }, + { + category: "Error", + file: "streams.ts", + message: "Property 'blob' does not exist on type 'ReadableStream>'.", + code: 2339, + }, + { + category: "Error", + file: "websocket.ts", + message: "Object literal may only specify known properties, and 'protocols' does not exist in type 'string[]'.", + code: 2353, + }, + { + category: "Error", + file: "websocket.ts", + message: "Object literal may only specify known properties, and 'protocol' does not exist in type 'string[]'.", + code: 2353, + }, + { + category: "Error", + file: "websocket.ts", + message: "Object literal may only specify known properties, and 'protocol' does not exist in type 'string[]'.", + code: 2353, + }, + { + category: "Error", + file: "websocket.ts", + message: "Object literal may only specify known properties, and 'headers' does not exist in type 'string[]'.", + code: 2353, + }, + { + category: "Error", + file: "websocket.ts", + message: "Object literal may only specify known properties, and 'protocols' does not exist in type 'string[]'.", + code: 2353, + }, + { + category: "Error", + file: "websocket.ts", + message: "Expected 2 arguments, but got 0.", + code: 2554, + }, + { + category: "Error", + file: "websocket.ts", + message: "Property 'URL' does not exist on type 'WebSocket'. Did you mean 'url'?", + code: 2551, + }, + { + category: "Error", + file: "websocket.ts", + message: "Type '\"nodebuffer\"' is not assignable to type 'BinaryType'.", + code: 2322, + }, + { + category: "Error", + file: "websocket.ts", + message: "Property 'ping' does not exist on type 'WebSocket'.", + code: 2339, + }, + { + category: "Error", + file: "websocket.ts", + message: "Property 'ping' does not exist on type 'WebSocket'.", + code: 2339, + }, + { + category: "Error", + file: "websocket.ts", + message: "Property 'ping' does not exist on type 'WebSocket'.", + code: 2339, + }, + { + category: "Error", + file: "websocket.ts", + message: "Property 'ping' does not exist on type 'WebSocket'.", + code: 2339, + }, + { + category: "Error", + file: "websocket.ts", + message: "Property 'pong' does not exist on type 'WebSocket'.", + code: 2339, + }, + { + category: "Error", + file: "websocket.ts", + message: "Property 'pong' does not exist on type 'WebSocket'.", + code: 2339, + }, + { + category: "Error", + file: "websocket.ts", + message: "Property 'pong' does not exist on type 'WebSocket'.", + code: 2339, + }, + { + category: "Error", + file: "websocket.ts", + message: "Property 'pong' does not exist on type 'WebSocket'.", + code: 2339, + }, + { + category: "Error", + file: "websocket.ts", + message: "Property 'terminate' does not exist on type 'WebSocket'.", + code: 2339, + }, + { + category: "Error", + file: "worker.ts", + message: "Property 'ref' does not exist on type 'Worker'.", + code: 2339, + }, + { + category: "Error", + file: "worker.ts", + message: "Property 'unref' does not exist on type 'Worker'.", + code: 2339, + }, + { + category: "Error", + file: "worker.ts", + message: "Property 'threadId' does not exist on type 'Worker'.", + code: 2339, + }, + ]); }); }); diff --git a/test/integration/bun-types/fixture/utilities.ts b/test/integration/bun-types/fixture/utilities.ts index 881f4df3e4..df761817af 100644 --- a/test/integration/bun-types/fixture/utilities.ts +++ b/test/integration/bun-types/fixture/utilities.ts @@ -34,5 +34,7 @@ export function expectType(arg?: T) { return { is() {}, extends() {} }; } +export declare function expectNotEmpty(...args: [keyof T] extends [never] ? [value: never] : [value?: T]): void; + export declare const expectAssignable: (expression: T) => void; export declare const expectTypeEquals: (expression: T extends S ? (S extends T ? true : false) : false) => void; diff --git a/test/package.json b/test/package.json index afa24d6521..dc3fdff3c2 100644 --- a/test/package.json +++ b/test/package.json @@ -87,7 +87,7 @@ "tsyringe": "4.8.0", "type-graphql": "2.0.0-rc.2", "typeorm": "0.3.20", - "typescript": "5.0.2", + "typescript": "5.8.3", "undici": "5.20.0", "uuid": "11.1.0", "unzipper": "0.12.3",