diff options
| author | Mohamed Bassem <me@mbassem.com> | 2025-02-01 18:16:25 +0000 |
|---|---|---|
| committer | Mohamed Bassem <me@mbassem.com> | 2025-02-01 18:16:25 +0000 |
| commit | fd7011aff5dd8ffde0fb10990da238f7baf9a814 (patch) | |
| tree | 99df3086a838ee33c40722d803c05c45a3a22ae3 | |
| parent | 0893446bed6cca753549ee8e3cf090f2fcf11d9d (diff) | |
| download | karakeep-fd7011aff5dd8ffde0fb10990da238f7baf9a814.tar.zst | |
fix: Abort all IO when workers timeout instead of detaching. Fixes #742
| -rw-r--r-- | apps/workers/crawlerWorker.ts | 75 | ||||
| -rw-r--r-- | apps/workers/openaiWorker.ts | 32 | ||||
| -rw-r--r-- | apps/workers/package.json | 2 | ||||
| -rw-r--r-- | apps/workers/videoWorker.ts | 5 | ||||
| -rw-r--r-- | package.json | 2 | ||||
| -rw-r--r-- | packages/shared/inference.ts | 49 | ||||
| -rw-r--r-- | packages/shared/package.json | 2 | ||||
| -rw-r--r-- | pnpm-lock.yaml | 180 | ||||
| -rw-r--r-- | tooling/typescript/node.json | 2 | ||||
| -rw-r--r-- | tooling/typescript/package.json | 2 |
10 files changed, 232 insertions, 119 deletions
diff --git a/apps/workers/crawlerWorker.ts b/apps/workers/crawlerWorker.ts index 6bb4f4ac..91adb185 100644 --- a/apps/workers/crawlerWorker.ts +++ b/apps/workers/crawlerWorker.ts @@ -237,12 +237,16 @@ function validateUrl(url: string) { } } -async function browserlessCrawlPage(jobId: string, url: string) { +async function browserlessCrawlPage( + jobId: string, + url: string, + abortSignal: AbortSignal, +) { logger.info( `[Crawler][${jobId}] Running in browserless mode. Will do a plain http request to "${url}". Screenshots will be disabled.`, ); const response = await fetch(url, { - signal: AbortSignal.timeout(5000), + signal: AbortSignal.any([AbortSignal.timeout(5000), abortSignal]), }); logger.info( `[Crawler][${jobId}] Successfully fetched the content of "${url}". Status: ${response.status}, Size: ${response.size}`, @@ -258,6 +262,7 @@ async function browserlessCrawlPage(jobId: string, url: string) { async function crawlPage( jobId: string, url: string, + abortSignal: AbortSignal, ): Promise<{ htmlContent: string; screenshot: Buffer | undefined; @@ -271,7 +276,7 @@ async function crawlPage( browser = globalBrowser; } if (!browser) { - return browserlessCrawlPage(jobId, url); + return browserlessCrawlPage(jobId, url, abortSignal); } const context = await browser.createBrowserContext(); @@ -412,10 +417,13 @@ async function downloadAndStoreFile( userId: string, jobId: string, fileType: string, + abortSignal: AbortSignal, ) { try { logger.info(`[Crawler][${jobId}] Downloading ${fileType} from "${url}"`); - const response = await fetch(url); + const response = await fetch(url, { + signal: abortSignal, + }); if (!response.ok) { throw new Error(`Failed to download ${fileType}: ${response.status}`); } @@ -451,6 +459,7 @@ async function downloadAndStoreImage( url: string, userId: string, jobId: string, + abortSignal: AbortSignal, ) { if (!serverConfig.crawler.downloadBannerImage) { logger.info( @@ -458,7 +467,7 @@ async function downloadAndStoreImage( ); return null; } - return downloadAndStoreFile(url, userId, jobId, "image"); + return downloadAndStoreFile(url, userId, jobId, "image", abortSignal); } async function archiveWebpage( @@ -466,6 +475,7 @@ async function archiveWebpage( url: string, userId: string, jobId: string, + abortSignal: AbortSignal, ) { logger.info(`[Crawler][${jobId}] Will attempt to archive page ...`); const assetId = newAssetId(); @@ -473,6 +483,7 @@ async function archiveWebpage( await execa({ input: html, + cancelSignal: abortSignal, })("monolith", ["-", "-Ije", "-t", "5", "-b", url, "-o", assetPath]); const contentType = "text/html"; @@ -500,6 +511,7 @@ async function archiveWebpage( async function getContentType( url: string, jobId: string, + abortSignal: AbortSignal, ): Promise<string | null> { try { logger.info( @@ -507,7 +519,7 @@ async function getContentType( ); const response = await fetch(url, { method: "HEAD", - signal: AbortSignal.timeout(5000), + signal: AbortSignal.any([AbortSignal.timeout(5000), abortSignal]), }); const contentType = response.headers.get("content-type"); logger.info( @@ -536,8 +548,15 @@ async function handleAsAssetBookmark( userId: string, jobId: string, bookmarkId: string, + abortSignal: AbortSignal, ) { - const downloaded = await downloadAndStoreFile(url, userId, jobId, assetType); + const downloaded = await downloadAndStoreFile( + url, + userId, + jobId, + assetType, + abortSignal, + ); if (!downloaded) { return; } @@ -586,6 +605,7 @@ async function crawlAndParseUrl( oldFullPageArchiveAssetId: string | undefined, precrawledArchiveAssetId: string | undefined, archiveFullPage: boolean, + abortSignal: AbortSignal, ) { let result: { htmlContent: string; @@ -609,8 +629,9 @@ async function crawlAndParseUrl( url, }; } else { - result = await crawlPage(jobId, url); + result = await crawlPage(jobId, url, abortSignal); } + abortSignal.throwIfAborted(); const { htmlContent, screenshot, statusCode, url: browserUrl } = result; @@ -619,9 +640,15 @@ async function crawlAndParseUrl( extractReadableContent(htmlContent, browserUrl, jobId), storeScreenshot(screenshot, userId, jobId), ]); + abortSignal.throwIfAborted(); let imageAssetInfo: DBAssetType | null = null; if (meta.image) { - const downloaded = await downloadAndStoreImage(meta.image, userId, jobId); + const downloaded = await downloadAndStoreImage( + meta.image, + userId, + jobId, + abortSignal, + ); if (downloaded) { imageAssetInfo = { id: downloaded.assetId, @@ -633,6 +660,7 @@ async function crawlAndParseUrl( }; } } + abortSignal.throwIfAborted(); // TODO(important): Restrict the size of content to store await db.transaction(async (txn) => { @@ -682,7 +710,13 @@ async function crawlAndParseUrl( assetId: fullPageArchiveAssetId, size, contentType, - } = await archiveWebpage(htmlContent, browserUrl, userId, jobId); + } = await archiveWebpage( + htmlContent, + browserUrl, + userId, + jobId, + abortSignal, + ); await db.transaction(async (txn) => { await updateAsset( @@ -732,19 +766,33 @@ async function runCrawler(job: DequeuedJob<ZCrawlLinkRequest>) { ); validateUrl(url); - const contentType = await getContentType(url, jobId); + const contentType = await getContentType(url, jobId, job.abortSignal); // Link bookmarks get transformed into asset bookmarks if they point to a supported asset instead of a webpage const isPdf = contentType === ASSET_TYPES.APPLICATION_PDF; if (isPdf) { - await handleAsAssetBookmark(url, "pdf", userId, jobId, bookmarkId); + await handleAsAssetBookmark( + url, + "pdf", + userId, + jobId, + bookmarkId, + job.abortSignal, + ); } else if ( contentType && IMAGE_ASSET_TYPES.has(contentType) && SUPPORTED_UPLOAD_ASSET_TYPES.has(contentType) ) { - await handleAsAssetBookmark(url, "image", userId, jobId, bookmarkId); + await handleAsAssetBookmark( + url, + "image", + userId, + jobId, + bookmarkId, + job.abortSignal, + ); } else { const archivalLogic = await crawlAndParseUrl( url, @@ -756,6 +804,7 @@ async function runCrawler(job: DequeuedJob<ZCrawlLinkRequest>) { oldFullPageArchiveAssetId, precrawledArchiveAssetId, archiveFullPage, + job.abortSignal, ); // Enqueue openai job (if not set, assume it's true for backward compatibility) diff --git a/apps/workers/openaiWorker.ts b/apps/workers/openaiWorker.ts index 704a6c04..ec5681c6 100644 --- a/apps/workers/openaiWorker.ts +++ b/apps/workers/openaiWorker.ts @@ -141,6 +141,7 @@ async function inferTagsFromImage( jobId: string, bookmark: NonNullable<Awaited<ReturnType<typeof fetchBookmark>>>, inferenceClient: InferenceClient, + abortSignal: AbortSignal, ) { const { asset, metadata } = await readAsset({ userId: bookmark.userId, @@ -161,7 +162,7 @@ async function inferTagsFromImage( ), metadata.contentType, base64, - { json: true }, + { json: true, abortSignal }, ); } @@ -226,6 +227,7 @@ async function inferTagsFromPDF( _jobId: string, bookmark: NonNullable<Awaited<ReturnType<typeof fetchBookmark>>>, inferenceClient: InferenceClient, + abortSignal: AbortSignal, ) { const prompt = buildTextPrompt( serverConfig.inference.inferredTagLang, @@ -233,15 +235,17 @@ async function inferTagsFromPDF( `Content: ${bookmark.asset.content}`, serverConfig.inference.contextLength, ); - return inferenceClient.inferFromText(prompt, { json: true }); + return inferenceClient.inferFromText(prompt, { json: true, abortSignal }); } async function inferTagsFromText( bookmark: NonNullable<Awaited<ReturnType<typeof fetchBookmark>>>, inferenceClient: InferenceClient, + abortSignal: AbortSignal, ) { return await inferenceClient.inferFromText(await buildPrompt(bookmark), { json: true, + abortSignal, }); } @@ -249,17 +253,28 @@ async function inferTags( jobId: string, bookmark: NonNullable<Awaited<ReturnType<typeof fetchBookmark>>>, inferenceClient: InferenceClient, + abortSignal: AbortSignal, ) { let response; if (bookmark.link || bookmark.text) { - response = await inferTagsFromText(bookmark, inferenceClient); + response = await inferTagsFromText(bookmark, inferenceClient, abortSignal); } else if (bookmark.asset) { switch (bookmark.asset.assetType) { case "image": - response = await inferTagsFromImage(jobId, bookmark, inferenceClient); + response = await inferTagsFromImage( + jobId, + bookmark, + inferenceClient, + abortSignal, + ); break; case "pdf": - response = await inferTagsFromPDF(jobId, bookmark, inferenceClient); + response = await inferTagsFromPDF( + jobId, + bookmark, + inferenceClient, + abortSignal, + ); break; default: throw new Error(`[inference][${jobId}] Unsupported bookmark type`); @@ -413,7 +428,12 @@ async function runOpenAI(job: DequeuedJob<ZOpenAIRequest>) { `[inference][${jobId}] Starting an inference job for bookmark with id "${bookmark.id}"`, ); - const tags = await inferTags(jobId, bookmark, inferenceClient); + const tags = await inferTags( + jobId, + bookmark, + inferenceClient, + job.abortSignal, + ); await connectTags(bookmarkId, tags, bookmark.userId); diff --git a/apps/workers/package.json b/apps/workers/package.json index e11a85d6..5a0c1b86 100644 --- a/apps/workers/package.json +++ b/apps/workers/package.json @@ -17,7 +17,7 @@ "drizzle-orm": "^0.38.3", "execa": "9.3.1", "jsdom": "^24.0.0", - "liteque": "^0.3.0", + "liteque": "^0.3.2", "metascraper": "^5.45.24", "metascraper-amazon": "^5.45.22", "metascraper-description": "^5.45.22", diff --git a/apps/workers/videoWorker.ts b/apps/workers/videoWorker.ts index 10f18454..32f16f97 100644 --- a/apps/workers/videoWorker.ts +++ b/apps/workers/videoWorker.ts @@ -104,7 +104,9 @@ async function runWorker(job: DequeuedJob<ZVideoRequest>) { `[VideoCrawler][${jobId}] Attempting to download a file from "${url}" to "${assetPath}" using the following arguments: "${ytDlpArguments}"`,
);
- await execa("yt-dlp", ytDlpArguments);
+ await execa("yt-dlp", ytDlpArguments, {
+ cancelSignal: job.abortSignal,
+ });
const downloadPath = await findAssetFile(videoAssetId);
if (!downloadPath) {
logger.info(
@@ -124,7 +126,6 @@ async function runWorker(job: DequeuedJob<ZVideoRequest>) { );
return;
}
- console.log(JSON.stringify(err));
logger.error(
`[VideoCrawler][${jobId}] Failed to download a file from "${url}" to "${assetPath}"`,
);
diff --git a/package.json b/package.json index eb8fc9d7..04b88023 100644 --- a/package.json +++ b/package.json @@ -22,7 +22,7 @@ "devDependencies": { "@hoarder/prettier-config": "workspace:^0.1.0", "@tanstack/eslint-plugin-query": "^5.20.1", - "@types/node": "^20", + "@types/node": "^22", "es-errors": "^1.3.0", "eslint": "^8.57.0", "husky": "^9.0.11", diff --git a/packages/shared/inference.ts b/packages/shared/inference.ts index 1573382f..f1bea9ff 100644 --- a/packages/shared/inference.ts +++ b/packages/shared/inference.ts @@ -15,6 +15,7 @@ export interface EmbeddingResponse { export interface InferenceOptions { json: boolean; + abortSignal?: AbortSignal; } const defaultInferenceOptions: InferenceOptions = { @@ -24,13 +25,13 @@ const defaultInferenceOptions: InferenceOptions = { export interface InferenceClient { inferFromText( prompt: string, - opts: InferenceOptions, + opts: Partial<InferenceOptions>, ): Promise<InferenceResponse>; inferFromImage( prompt: string, contentType: string, image: string, - opts: InferenceOptions, + opts: Partial<InferenceOptions>, ): Promise<InferenceResponse>; generateEmbeddingFromText(inputs: string[]): Promise<EmbeddingResponse>; } @@ -60,12 +61,18 @@ class OpenAIInferenceClient implements InferenceClient { async inferFromText( prompt: string, - opts: InferenceOptions = defaultInferenceOptions, + _opts: Partial<InferenceOptions>, ): Promise<InferenceResponse> { + const optsWithDefaults: InferenceOptions = { + ...defaultInferenceOptions, + ..._opts, + }; const chatCompletion = await this.openAI.chat.completions.create({ messages: [{ role: "user", content: prompt }], model: serverConfig.inference.textModel, - response_format: opts.json ? { type: "json_object" } : undefined, + response_format: optsWithDefaults.json + ? { type: "json_object" } + : undefined, }); const response = chatCompletion.choices[0].message.content; @@ -79,11 +86,17 @@ class OpenAIInferenceClient implements InferenceClient { prompt: string, contentType: string, image: string, - opts: InferenceOptions = defaultInferenceOptions, + _opts: Partial<InferenceOptions>, ): Promise<InferenceResponse> { + const optsWithDefaults: InferenceOptions = { + ...defaultInferenceOptions, + ..._opts, + }; const chatCompletion = await this.openAI.chat.completions.create({ model: serverConfig.inference.imageModel, - response_format: opts.json ? { type: "json_object" } : undefined, + response_format: optsWithDefaults.json + ? { type: "json_object" } + : undefined, messages: [ { role: "user", @@ -136,12 +149,16 @@ class OllamaInferenceClient implements InferenceClient { async runModel( model: string, prompt: string, + _opts: InferenceOptions, image?: string, - opts: InferenceOptions = defaultInferenceOptions, ) { + const optsWithDefaults: InferenceOptions = { + ...defaultInferenceOptions, + ..._opts, + }; const chatCompletion = await this.ollama.chat({ model: model, - format: opts.json ? "json" : undefined, + format: optsWithDefaults.json ? "json" : undefined, stream: true, keep_alive: serverConfig.inference.ollamaKeepAlive, options: { @@ -179,13 +196,17 @@ class OllamaInferenceClient implements InferenceClient { async inferFromText( prompt: string, - opts: InferenceOptions = defaultInferenceOptions, + _opts: Partial<InferenceOptions>, ): Promise<InferenceResponse> { + const optsWithDefaults: InferenceOptions = { + ...defaultInferenceOptions, + ..._opts, + }; return await this.runModel( serverConfig.inference.textModel, prompt, + optsWithDefaults, undefined, - opts, ); } @@ -193,13 +214,17 @@ class OllamaInferenceClient implements InferenceClient { prompt: string, _contentType: string, image: string, - opts: InferenceOptions = defaultInferenceOptions, + _opts: Partial<InferenceOptions>, ): Promise<InferenceResponse> { + const optsWithDefaults: InferenceOptions = { + ...defaultInferenceOptions, + ..._opts, + }; return await this.runModel( serverConfig.inference.imageModel, prompt, + optsWithDefaults, image, - opts, ); } diff --git a/packages/shared/package.json b/packages/shared/package.json index 93d5495a..ecb16013 100644 --- a/packages/shared/package.json +++ b/packages/shared/package.json @@ -6,7 +6,7 @@ "type": "module", "dependencies": { "glob": "^11.0.0", - "liteque": "^0.3.0", + "liteque": "^0.3.2", "meilisearch": "^0.37.0", "ollama": "^0.5.9", "openai": "^4.67.1", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index f7015d16..f00c0b2a 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -20,8 +20,8 @@ importers: specifier: ^5.20.1 version: 5.20.1(eslint@8.57.0)(typescript@5.7.3) '@types/node': - specifier: ^20 - version: 20.11.20 + specifier: ^22 + version: 22.13.0 es-errors: specifier: ^1.3.0 version: 1.3.0 @@ -148,7 +148,7 @@ importers: version: 18.2.19 '@vitejs/plugin-react-swc': specifier: ^3.5.0 - version: 3.6.0(vite@5.1.4(@types/node@20.11.20)) + version: 3.6.0(vite@5.1.4(@types/node@22.13.0)) autoprefixer: specifier: ^10.4.17 version: 10.4.17(postcss@8.4.35) @@ -172,7 +172,7 @@ importers: version: 5.7.3 vite: specifier: ^5.1.0 - version: 5.1.4(@types/node@20.11.20) + version: 5.1.4(@types/node@22.13.0) apps/cli: devDependencies: @@ -220,7 +220,7 @@ importers: version: 4.7.1 vite: specifier: ^5.1.0 - version: 5.1.4(@types/node@20.11.20) + version: 5.1.4(@types/node@22.13.0) apps/landing: dependencies: @@ -721,7 +721,7 @@ importers: version: 4.3.1(typescript@5.7.3) vitest: specifier: ^1.3.1 - version: 1.3.1(@types/node@20.11.20) + version: 1.3.1(@types/node@22.13.0) apps/workers: dependencies: @@ -765,8 +765,8 @@ importers: specifier: ^24.0.0 version: 24.0.0 liteque: - specifier: ^0.3.0 - version: 0.3.0(better-sqlite3@11.3.0) + specifier: ^0.3.2 + version: 0.3.2(better-sqlite3@11.3.0) metascraper: specifier: ^5.45.24 version: 5.45.24 @@ -965,7 +965,7 @@ importers: version: 4.3.1(typescript@5.7.3) vitest: specifier: ^1.3.1 - version: 1.3.1(@types/node@20.11.20) + version: 1.3.1(@types/node@22.13.0) packages/open-api: dependencies: @@ -1015,10 +1015,10 @@ importers: version: 4.7.1 vite: specifier: ^5.1.0 - version: 5.1.4(@types/node@20.11.20) + version: 5.1.4(@types/node@22.13.0) vite-plugin-dts: specifier: ^4.4.0 - version: 4.4.0(@types/node@20.11.20)(typescript@5.7.3)(vite@5.1.4(@types/node@20.11.20)) + version: 4.4.0(@types/node@22.13.0)(typescript@5.7.3)(vite@5.1.4(@types/node@22.13.0)) packages/shared: dependencies: @@ -1026,8 +1026,8 @@ importers: specifier: ^11.0.0 version: 11.0.0 liteque: - specifier: ^0.3.0 - version: 0.3.0(better-sqlite3@11.3.0) + specifier: ^0.3.2 + version: 0.3.2(better-sqlite3@11.3.0) meilisearch: specifier: ^0.37.0 version: 0.37.0 @@ -1058,7 +1058,7 @@ importers: version: link:../../tooling/typescript vitest: specifier: ^1.3.1 - version: 1.3.1(@types/node@20.11.20) + version: 1.3.1(@types/node@22.13.0) packages/shared-react: dependencies: @@ -1138,7 +1138,7 @@ importers: version: 4.3.1(typescript@5.7.3) vitest: specifier: ^1.3.1 - version: 1.3.1(@types/node@20.11.20) + version: 1.3.1(@types/node@22.13.0) tooling/eslint: dependencies: @@ -1246,9 +1246,9 @@ importers: tooling/typescript: devDependencies: - '@tsconfig/node21': - specifier: ^21.0.1 - version: 21.0.1 + '@tsconfig/node22': + specifier: ^22.0.0 + version: 22.0.0 packages: @@ -4684,6 +4684,9 @@ packages: '@tsconfig/node21@21.0.1': resolution: {integrity: sha512-2Khg79N+z2Qkb9SjLzOi8cz2PSa/oUpHIeQm1YWzmWXkoFcPXFZSHgs+Z8iPCDjIoXFqMNYntiTXxfLYQMcRhw==} + '@tsconfig/node22@22.0.0': + resolution: {integrity: sha512-twLQ77zevtxobBOD4ToAtVmuYrpeYUh3qh+TEp+08IWhpsrIflVHqQ1F1CiPxQGL7doCdBIOOCF+1Tm833faNg==} + '@types/acorn@4.0.6': resolution: {integrity: sha512-veQTnWP+1D/xbxVrPC3zHnCZRjSrKfhbMUlEA43iMZLu7EsnTtkJklIuwrCPbOi8YkvDQAiW05VQQFvvz9oieQ==} @@ -4868,6 +4871,9 @@ packages: '@types/node@20.11.20': resolution: {integrity: sha512-7/rR21OS+fq8IyHTgtLkDK949uzsa6n8BkziAKtPVpugIkO6D+/ooXMvzXxDnZrmtXVfjb1bKQafYpb8s89LOg==} + '@types/node@22.13.0': + resolution: {integrity: sha512-ClIbNe36lawluuvq3+YYhnIN2CELi+6q8NpnM7PYp4hBn/TatfboPgVSm2rwKRfnV2M+Ty9GWDFI64KEe+kysA==} + '@types/parse-json@4.0.2': resolution: {integrity: sha512-dISoDXWWQwUquiKsyZ4Ng+HX2KsPL7LyHKHQwgGFEA3IaKac4Obd+h2a/a6waisAoepJlBcx9paWqjA8/HVjCw==} @@ -9207,8 +9213,8 @@ packages: resolution: {integrity: sha512-wUayTU8MS827Dam6MxgD72Ui+KOSF+u/eIqpatOtjnvgJ0+mnDq33uC2M7J0tPK+upe/DpUAuK4JUU89iBoNKQ==} engines: {node: '>=4'} - liteque@0.3.0: - resolution: {integrity: sha512-cyfkoGpXt+MpKrc8yQbakeup9IIWeTBvh93llNmBB+G+i0ZrCei2XXZxNyenJtADf8KZlzKHX6fkmFb1/MahBA==} + liteque@0.3.2: + resolution: {integrity: sha512-adBWSpayJ+Pfl0q5/AL4uehYvrLHAaDiqMsccWNGDZo2xgZ0LaZeDomttVBoS4ZLBTDBxDXxgaYoCodD/s1AsA==} peerDependencies: better-sqlite3: '>=7' @@ -12890,6 +12896,9 @@ packages: undici-types@5.26.5: resolution: {integrity: sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==} + undici-types@6.20.0: + resolution: {integrity: sha512-Ny6QZ2Nju20vw1SRHe3d9jVu6gJ+4e3+MMpqu7pqE5HT6WsTSlce++GQmK5UXS8mzV8DSYHrQH+Xrf2jVcuKNg==} + undici@6.19.8: resolution: {integrity: sha512-U8uCCl2x9TK3WANvmBavymRzxbfFYG+tAu+fgx3zxQy3qdagQqBLwJVrdyO1TBfUXvfKveMKJZhpvUYoOjM+4g==} engines: {node: '>=18.17'} @@ -16824,7 +16833,7 @@ snapshots: dependencies: '@jest/fake-timers': 29.7.0 '@jest/types': 29.6.3 - '@types/node': 20.11.20 + '@types/node': 22.13.0 jest-mock: 29.7.0 dev: false @@ -16832,7 +16841,7 @@ snapshots: dependencies: '@jest/types': 29.6.3 '@sinonjs/fake-timers': 10.3.0 - '@types/node': 20.11.20 + '@types/node': 22.13.0 jest-message-util: 29.7.0 jest-mock: 29.7.0 jest-util: 29.7.0 @@ -16868,7 +16877,7 @@ snapshots: '@jest/schemas': 29.6.3 '@types/istanbul-lib-coverage': 2.0.6 '@types/istanbul-reports': 3.0.4 - '@types/node': 20.11.20 + '@types/node': 22.13.0 '@types/yargs': 17.0.32 chalk: 4.1.2 dev: false @@ -17176,24 +17185,24 @@ snapshots: - utf-8-validate dev: false - '@microsoft/api-extractor-model@7.30.1(@types/node@20.11.20)': + '@microsoft/api-extractor-model@7.30.1(@types/node@22.13.0)': dependencies: '@microsoft/tsdoc': 0.15.1 '@microsoft/tsdoc-config': 0.17.1 - '@rushstack/node-core-library': 5.10.1(@types/node@20.11.20) + '@rushstack/node-core-library': 5.10.1(@types/node@22.13.0) transitivePeerDependencies: - '@types/node' dev: true - '@microsoft/api-extractor@7.48.1(@types/node@20.11.20)': + '@microsoft/api-extractor@7.48.1(@types/node@22.13.0)': dependencies: - '@microsoft/api-extractor-model': 7.30.1(@types/node@20.11.20) + '@microsoft/api-extractor-model': 7.30.1(@types/node@22.13.0) '@microsoft/tsdoc': 0.15.1 '@microsoft/tsdoc-config': 0.17.1 - '@rushstack/node-core-library': 5.10.1(@types/node@20.11.20) + '@rushstack/node-core-library': 5.10.1(@types/node@22.13.0) '@rushstack/rig-package': 0.5.3 - '@rushstack/terminal': 0.14.4(@types/node@20.11.20) - '@rushstack/ts-command-line': 4.23.2(@types/node@20.11.20) + '@rushstack/terminal': 0.14.4(@types/node@22.13.0) + '@rushstack/ts-command-line': 4.23.2(@types/node@22.13.0) lodash: 4.17.21 minimatch: 3.0.8 resolve: 1.22.8 @@ -18392,9 +18401,9 @@ snapshots: dev: true optional: true - '@rushstack/node-core-library@5.10.1(@types/node@20.11.20)': + '@rushstack/node-core-library@5.10.1(@types/node@22.13.0)': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 ajv: 8.13.0 ajv-draft-04: 1.0.0(ajv@8.13.0) ajv-formats: 3.0.1(ajv@8.13.0) @@ -18411,16 +18420,16 @@ snapshots: strip-json-comments: 3.1.1 dev: true - '@rushstack/terminal@0.14.4(@types/node@20.11.20)': + '@rushstack/terminal@0.14.4(@types/node@22.13.0)': dependencies: - '@rushstack/node-core-library': 5.10.1(@types/node@20.11.20) - '@types/node': 20.11.20 + '@rushstack/node-core-library': 5.10.1(@types/node@22.13.0) + '@types/node': 22.13.0 supports-color: 8.1.1 dev: true - '@rushstack/ts-command-line@4.23.2(@types/node@20.11.20)': + '@rushstack/ts-command-line@4.23.2(@types/node@22.13.0)': dependencies: - '@rushstack/terminal': 0.14.4(@types/node@20.11.20) + '@rushstack/terminal': 0.14.4(@types/node@22.13.0) '@types/argparse': 1.0.38 argparse: 1.0.10 string-argv: 0.3.2 @@ -18736,6 +18745,9 @@ snapshots: '@tsconfig/node21@21.0.1': {} + '@tsconfig/node22@22.0.0': + dev: true + '@types/acorn@4.0.6': dependencies: '@types/estree': 1.0.5 @@ -18778,19 +18790,19 @@ snapshots: '@types/body-parser@1.19.5': dependencies: '@types/connect': 3.4.38 - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/bonjour@3.5.13': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/cacheable-request@6.0.3': dependencies: '@types/http-cache-semantics': 4.0.4 '@types/keyv': 3.1.4 - '@types/node': 20.11.20 + '@types/node': 22.13.0 '@types/responselike': 1.0.3 dev: false @@ -18803,12 +18815,12 @@ snapshots: '@types/connect-history-api-fallback@1.5.4': dependencies: '@types/express-serve-static-core': 4.17.43 - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/connect@3.4.38': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/cookie@0.6.0': @@ -18854,7 +18866,7 @@ snapshots: '@types/express-serve-static-core@4.17.43': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 '@types/qs': 6.9.13 '@types/range-parser': 1.2.7 '@types/send': 0.17.4 @@ -18879,12 +18891,12 @@ snapshots: '@types/glob@7.2.0': dependencies: '@types/minimatch': 5.1.2 - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/graceful-fs@4.1.9': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/gtag.js@0.0.12': @@ -18924,7 +18936,7 @@ snapshots: '@types/http-proxy@1.17.14': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/istanbul-lib-coverage@2.0.6': @@ -18953,7 +18965,7 @@ snapshots: '@types/keyv@3.1.4': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/mdast@4.0.3': @@ -18981,13 +18993,13 @@ snapshots: '@types/node-fetch@2.6.11': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 form-data: 4.0.0 dev: false '@types/node-forge@1.3.11': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/node@17.0.45': @@ -19002,6 +19014,10 @@ snapshots: dependencies: undici-types: 5.26.5 + '@types/node@22.13.0': + dependencies: + undici-types: 6.20.0 + '@types/parse-json@4.0.2': dev: false @@ -19073,12 +19089,12 @@ snapshots: '@types/resolve@1.17.1': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/responselike@1.0.3': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/retry@0.12.0': @@ -19086,7 +19102,7 @@ snapshots: '@types/sax@1.2.7': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/scheduler@0.16.8': {} @@ -19097,7 +19113,7 @@ snapshots: '@types/send@0.17.4': dependencies: '@types/mime': 1.3.5 - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/serve-index@1.9.4': @@ -19109,12 +19125,12 @@ snapshots: dependencies: '@types/http-errors': 2.0.4 '@types/mime': 3.0.4 - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/sockjs@0.3.36': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/stack-utils@2.0.3': @@ -19134,7 +19150,7 @@ snapshots: '@types/ws@8.5.10': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false '@types/yargs-parser@21.0.3': @@ -19147,7 +19163,7 @@ snapshots: '@types/yauzl@2.10.3': dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 dev: false optional: true @@ -19348,10 +19364,10 @@ snapshots: wonka: 6.3.4 dev: false - '@vitejs/plugin-react-swc@3.6.0(vite@5.1.4(@types/node@20.11.20))': + '@vitejs/plugin-react-swc@3.6.0(vite@5.1.4(@types/node@22.13.0))': dependencies: '@swc/core': 1.4.2 - vite: 5.1.4(@types/node@20.11.20) + vite: 5.1.4(@types/node@22.13.0) transitivePeerDependencies: - '@swc/helpers' dev: true @@ -20594,7 +20610,7 @@ snapshots: chrome-launcher@0.15.2: dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 escape-string-regexp: 4.0.0 is-wsl: 2.2.0 lighthouse-logger: 1.4.2 @@ -20613,7 +20629,7 @@ snapshots: chromium-edge-launcher@0.2.0: dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 escape-string-regexp: 4.0.0 is-wsl: 2.2.0 lighthouse-logger: 1.4.2 @@ -22317,7 +22333,7 @@ snapshots: eval@0.1.8: dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 require-like: 0.1.2 dev: false @@ -24317,7 +24333,7 @@ snapshots: '@jest/environment': 29.7.0 '@jest/fake-timers': 29.7.0 '@jest/types': 29.6.3 - '@types/node': 20.11.20 + '@types/node': 22.13.0 jest-mock: 29.7.0 jest-util: 29.7.0 dev: false @@ -24329,7 +24345,7 @@ snapshots: dependencies: '@jest/types': 29.6.3 '@types/graceful-fs': 4.1.9 - '@types/node': 20.11.20 + '@types/node': 22.13.0 anymatch: 3.1.3 fb-watchman: 2.0.2 graceful-fs: 4.2.11 @@ -24358,7 +24374,7 @@ snapshots: jest-mock@29.7.0: dependencies: '@jest/types': 29.6.3 - '@types/node': 20.11.20 + '@types/node': 22.13.0 jest-util: 29.7.0 dev: false @@ -24368,7 +24384,7 @@ snapshots: jest-util@29.7.0: dependencies: '@jest/types': 29.6.3 - '@types/node': 20.11.20 + '@types/node': 22.13.0 chalk: 4.1.2 ci-info: 3.9.0 graceful-fs: 4.2.11 @@ -24387,20 +24403,20 @@ snapshots: jest-worker@26.6.2: dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 merge-stream: 2.0.0 supports-color: 7.2.0 dev: false jest-worker@27.5.1: dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 merge-stream: 2.0.0 supports-color: 8.1.1 jest-worker@29.7.0: dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 jest-util: 29.7.0 merge-stream: 2.0.0 supports-color: 8.1.1 @@ -24762,7 +24778,7 @@ snapshots: liquid-json@0.3.1: dev: false - liteque@0.3.0(better-sqlite3@11.3.0): + liteque@0.3.2(better-sqlite3@11.3.0): dependencies: async-mutex: 0.4.1 better-sqlite3: 11.3.0 @@ -30012,6 +30028,8 @@ snapshots: undici-types@5.26.5: {} + undici-types@6.20.0: {} + undici@6.19.8: {} unicode-canonical-property-names-ecmascript@2.0.0: @@ -30290,13 +30308,13 @@ snapshots: video-extensions@1.2.0: dev: false - vite-node@1.3.1(@types/node@20.11.20): + vite-node@1.3.1(@types/node@22.13.0): dependencies: cac: 6.7.14 debug: 4.3.7 pathe: 1.1.2 picocolors: 1.1.1 - vite: 5.1.4(@types/node@20.11.20) + vite: 5.1.4(@types/node@22.13.0) transitivePeerDependencies: - '@types/node' - less @@ -30308,9 +30326,9 @@ snapshots: - terser dev: true - vite-plugin-dts@4.4.0(@types/node@20.11.20)(typescript@5.7.3)(vite@5.1.4(@types/node@20.11.20)): + vite-plugin-dts@4.4.0(@types/node@22.13.0)(typescript@5.7.3)(vite@5.1.4(@types/node@22.13.0)): dependencies: - '@microsoft/api-extractor': 7.48.1(@types/node@20.11.20) + '@microsoft/api-extractor': 7.48.1(@types/node@22.13.0) '@rollup/pluginutils': 5.1.4 '@volar/typescript': 2.4.11 '@vue/language-core': 2.1.10(typescript@5.7.3) @@ -30320,7 +30338,7 @@ snapshots: local-pkg: 0.5.1 magic-string: 0.30.17 typescript: 5.7.3 - vite: 5.1.4(@types/node@20.11.20) + vite: 5.1.4(@types/node@22.13.0) transitivePeerDependencies: - '@types/node' - rollup @@ -30337,9 +30355,9 @@ snapshots: - typescript dev: true - vite@5.1.4(@types/node@20.11.20): + vite@5.1.4(@types/node@22.13.0): dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 esbuild: 0.19.12 postcss: 8.4.47 rollup: 4.12.0 @@ -30347,9 +30365,9 @@ snapshots: fsevents: 2.3.3 dev: true - vitest@1.3.1(@types/node@20.11.20): + vitest@1.3.1(@types/node@22.13.0): dependencies: - '@types/node': 20.11.20 + '@types/node': 22.13.0 '@vitest/expect': 1.3.1 '@vitest/runner': 1.3.1 '@vitest/snapshot': 1.3.1 @@ -30367,8 +30385,8 @@ snapshots: strip-literal: 2.0.0 tinybench: 2.6.0 tinypool: 0.8.2 - vite: 5.1.4(@types/node@20.11.20) - vite-node: 1.3.1(@types/node@20.11.20) + vite: 5.1.4(@types/node@22.13.0) + vite-node: 1.3.1(@types/node@22.13.0) why-is-node-running: 2.2.2 transitivePeerDependencies: - less diff --git a/tooling/typescript/node.json b/tooling/typescript/node.json index aeda1ffd..288f6e63 100644 --- a/tooling/typescript/node.json +++ b/tooling/typescript/node.json @@ -1,6 +1,6 @@ { "$schema": "https://json.schemastore.org/tsconfig", - "extends": "@tsconfig/node21/tsconfig.json", + "extends": "@tsconfig/node22/tsconfig.json", "include": ["**/*.ts"], "exclude": ["node_modules", "build", "dist", ".next", ".expo"], "compilerOptions": { diff --git a/tooling/typescript/package.json b/tooling/typescript/package.json index f4885014..885f8473 100644 --- a/tooling/typescript/package.json +++ b/tooling/typescript/package.json @@ -7,6 +7,6 @@ "node.json" ], "devDependencies": { - "@tsconfig/node21": "^21.0.1" + "@tsconfig/node22": "^22.0.0" } } |
