Files
callstack__agent-device/scripts/size-report-install.mjs
Michał Pierzchała b15121ffc8 test(ios): establish snapshot convergence baselines and permanent evidence (#2204)
* test(ios): add snapshot convergence evidence harness

* fix(ios): satisfy benchmark CI guards

* fix(ios): constrain benchmark proxy routes

* fix(ios-benchmark): enforce cell admission evidence

* fix(ios-benchmark): protect benchmark state ownership

* fix(ios-benchmark): use proxy port flag

* fix(ios-benchmark): let proxy choose an ephemeral port

* test(ios-benchmark): keep CLI process seam local

* fix(ios-benchmark): parse proxy startup envelope

* fix(ios-benchmark): bind proxy lease to simulator

* fix(ios-benchmark): keep fresh proxy CLI sessions isolated

* fix(ios-benchmark): preserve async timeout evidence

* docs(ios-benchmark): retain exact-head evidence

* test(ios): reveal offscreen alert fixture controls

* test(ios): reset alert between relaunch samples

* test(ios): admit native alert snapshots

* docs(ios): publish snapshot convergence corpus

* chore(ios): format benchmark evidence

* fix(ios-benchmark): admit proxy fixture anchors

* docs(ios): republish exact-head benchmark corpus

* fix(size): make publish asset evidence hermetic

* style(size): format package evidence test

* test(size): update publish preparation contracts

* fix: retire stale utils layering zone

* test: pin shared publish asset owner

* test: verify preserved size reporter closure

* fix: move mutation ownership to snapshot module

* test(ios): add snapshot convergence evidence harness

* fix(ios): satisfy benchmark CI guards

* fix(ios): constrain benchmark proxy routes

* fix(ios-benchmark): enforce cell admission evidence

* fix(ios-benchmark): protect benchmark state ownership

* fix(ios-benchmark): use proxy port flag

* fix(ios-benchmark): let proxy choose an ephemeral port

* test(ios-benchmark): keep CLI process seam local

* fix(ios-benchmark): parse proxy startup envelope

* fix(ios-benchmark): bind proxy lease to simulator

* fix(ios-benchmark): keep fresh proxy CLI sessions isolated

* fix(ios-benchmark): preserve async timeout evidence

* docs(ios-benchmark): retain exact-head evidence

* test(ios): reveal offscreen alert fixture controls

* test(ios): reset alert between relaunch samples

* test(ios): admit native alert snapshots

* docs(ios): publish snapshot convergence corpus

* chore(ios): format benchmark evidence

* fix(ios-benchmark): admit proxy fixture anchors

* docs(ios): republish exact-head benchmark corpus

* fix(size): make publish asset evidence hermetic

* test(size): update publish preparation contracts

* fix: keep git-state gates out of mutation sandboxes
2026-09-01 21:39:05 +02:00

69 lines
2.0 KiB
JavaScript

import { execFileSync } from 'node:child_process';
import fs from 'node:fs';
import os from 'node:os';
import path from 'node:path';
export function measureCleanInstalledPackage(tarballPath, packageName) {
const workDir = fs.mkdtempSync(path.join(os.tmpdir(), 'agent-device-size-install-'));
const consumerDir = path.join(workDir, 'consumer');
const npmCache = path.join(workDir, 'npm-cache');
fs.mkdirSync(consumerDir);
fs.mkdirSync(npmCache);
try {
execFileSync(
'npm',
[
'install',
'--ignore-scripts',
'--no-audit',
'--no-fund',
'--package-lock=false',
'--prefix',
consumerDir,
tarballPath,
],
{
cwd: consumerDir,
env: { ...process.env, npm_config_cache: npmCache },
stdio: ['ignore', 'ignore', 'inherit'],
timeout: 5 * 60 * 1000,
},
);
const packageDir = path.join(consumerDir, 'node_modules', packageName);
if (!fs.existsSync(packageDir)) {
throw new Error(`Clean install did not create node_modules/${packageName}.`);
}
return measureDirectory(packageDir);
} finally {
fs.rmSync(workDir, { recursive: true, force: true });
}
}
export function measureDirectory(root) {
const entries = fs.readdirSync(root, { withFileTypes: true });
return entries.reduce(
(total, entry) => {
const entryPath = path.join(root, entry.name);
if (entry.isDirectory()) {
const nested = measureDirectory(entryPath);
return {
packageBytes: total.packageBytes + nested.packageBytes,
files: total.files + nested.files,
};
}
if (entry.isSymbolicLink()) {
return {
packageBytes: total.packageBytes + Buffer.byteLength(fs.readlinkSync(entryPath)),
files: total.files + 1,
};
}
const stat = fs.statSync(entryPath);
return {
packageBytes: total.packageBytes + stat.size,
files: total.files + 1,
};
},
{ packageBytes: 0, files: 0 },
);
}