perf(studio): speed up nitro scan and stop the cleanup panel freezing
CI / check (push) Successful in 4m13s
CI / preflight (push) Skipped
CI / deploy (push) Successful in 2m0s

This commit is contained in:
openhands committed 2026-09-19 11:39:19 +02:00
1 parent 91e649398c
commit c916e42572
2 files changed
+77 -42

No files matched your search

+11 -4
View File
@@ -217,14 +217,21 @@ interface DirectoryRead {
lastModified: number;
}
/**
* How many `stat` calls run in parallel while reading an asset directory.
* Directories can hold hundreds of thousands of files; serial `stat`ing them
* is the single biggest cost of the scan, so the work is spread over a pool.
*/
const DIR_STAT_CONCURRENCY = 32;
async function readAssetDir(
dir: string,
regex: RegExp,
): Promise<DirectoryRead[]> {
const names = await fs.readdir(dir).catch(() => [] as string[]);
const entries: DirectoryRead[] = [];
for (const name of names) {
if (!regex.test(name)) continue;
await runPool(names, DIR_STAT_CONCURRENCY, async (name) => {
if (!regex.test(name)) return;
let size = 0;
let mtimeMs = 0;
try {
@@ -240,7 +247,7 @@ async function readAssetDir(
size,
lastModified: mtimeMs,
});
}
});
return entries;
}
@@ -321,7 +328,7 @@ export async function scanFakeBrokenNitros(): Promise<NitroCleanupScan> {
const fake: NitroCleanupEntry[] = [];
const broken: NitroCleanupEntry[] = [];
await runPool(entries, 8, async (entry) => {
await runPool(entries, 16, async (entry) => {
// A .nitro that no DB item maps to is a leftover / fake bundle.
if (!validStems.has(entry.base.toLowerCase())) {
fake.push(entry);