Files
vercel__eve/scripts/nitro-bundle-report-budget.mjs
T
Andrew Barba f44e16a3e5 Hello Eve (#1)
Co-authored-by: Casey Gowrie <ctgowrie@gmail.com>
Co-authored-by: Allen Zhou <46854522+allenzhou101@users.noreply.github.com>
Co-authored-by: Rui Conti <ruiconti@gmail.com>
Co-authored-by: JJ Kasper <jj@jjsweb.site>
Co-authored-by: Timo Lins <1440854+timolins@users.noreply.github.com>
Co-authored-by: Felix Arntz <3531426+felixarntz@users.noreply.github.com>
Co-authored-by: Shar Dara <2982650+darafsheh@users.noreply.github.com>
Co-authored-by: John Phamous <johnphammail@gmail.com>
2026-06-16 18:10:54 +01:00

135 lines
3.5 KiB
JavaScript

import { readFile } from "node:fs/promises";
import { resolve } from "node:path";
import { fileURLToPath } from "node:url";
function formatBytes(bytes) {
if (bytes < 1_000) {
return `${bytes} B`;
}
if (bytes < 1_000_000) {
return `${(bytes / 1_000).toFixed(1)} kB`;
}
return `${(bytes / 1_000_000).toFixed(2)} MB`;
}
function formatRatioPercent(ratio) {
if (!Number.isFinite(ratio)) {
return "new";
}
return `${(ratio * 100).toFixed(1)}%`;
}
function formatFailure(check) {
if (check.kind === "runtime-dependency") {
return `New runtime dependency ${check.dependency} was added. Runtime dependencies increase the install footprint; prefer a vendored devDependency when possible`;
}
return `${check.metric} grew ${formatRatioPercent(check.increaseRatio)} (${formatBytes(check.baseline)} -> ${formatBytes(check.current)}), above the ${formatRatioPercent(check.thresholdRatio)} limit`;
}
function printUsage() {
process.stdout.write(
[
"Usage: node ./scripts/nitro-bundle-report-budget.mjs --report-json <path> [options]",
"",
"Options:",
" --report-json <path> Bundle report JSON generated by nitro-bundle-report.mjs",
" --acknowledged Allow budget failures to pass",
" --help Show this help text",
"",
].join("\n"),
);
}
function parseArguments(argv) {
const parsedArguments = {
acknowledged: false,
reportJsonPath: null,
};
for (let index = 0; index < argv.length; index += 1) {
const argument = argv[index];
if (argument === "--help") {
printUsage();
process.exit(0);
}
if (argument === "--acknowledged") {
parsedArguments.acknowledged = true;
continue;
}
const value = argv[index + 1];
if (value === undefined) {
throw new Error(`Missing value for "${argument}".`);
}
if (argument === "--report-json") {
parsedArguments.reportJsonPath = value;
index += 1;
continue;
}
throw new Error(`Unknown argument "${argument}".`);
}
if (parsedArguments.reportJsonPath === null) {
throw new Error('The "--report-json" option is required.');
}
return parsedArguments;
}
async function main() {
const args = parseArguments(process.argv.slice(2));
const report = JSON.parse(await readFile(resolve(args.reportJsonPath), "utf8"));
const sizeBudget = report.comparison?.sizeBudget;
if (!sizeBudget) {
process.stdout.write("No baseline comparison is available; skipping bundle warning policy.\n");
return;
}
const failures = sizeBudget.checks.filter((check) => check.failed);
if (failures.length === 0) {
process.stdout.write("Bundle warning policy passed.\n");
return;
}
const messageLines = [
"Bundle warning policy exceeded:",
...failures.map((failure) => `- ${formatFailure(failure)}`),
"",
"The pull request comment contains the same failure details.",
];
if (args.acknowledged) {
process.stdout.write(
`${messageLines.join("\n")}\nThe acknowledge-bundle-warning label is present, so this check is passing.\n`,
);
return;
}
process.stderr.write(
`${messageLines.join("\n")}\nAdd the acknowledge-bundle-warning label to acknowledge the regression and pass without regenerating the report.\n`,
);
process.exitCode = 1;
}
const executedScriptPath = process.argv[1] ? resolve(process.argv[1]) : null;
const moduleScriptPath = resolve(fileURLToPath(import.meta.url));
if (
executedScriptPath !== null &&
moduleScriptPath !== null &&
executedScriptPath === moduleScriptPath
) {
await main();
}