fix(cli): preflight browser archive extraction (#2469)

This commit is contained in:
Miguel Ángel
2026-07-15 02:29:33 -04:00
committed by GitHub
parent f3800f3579
commit d2aa4f8bc4
2 changed files with 63 additions and 1 deletions
+30
View File
@@ -88,6 +88,36 @@ describe("parseToolVersion", () => {
});
});
describe("checkArchiveExtractor", () => {
it("reports a missing unzip dependency on non-Windows hosts", async () => {
const doctor = await import("./doctor.js");
expect(doctor).toHaveProperty("checkArchiveExtractor");
const result = doctor.checkArchiveExtractor("linux", () => false);
expect(result).toEqual({
ok: false,
detail: "Not found",
hint: "Install unzip so HyperFrames can extract its managed Chrome download.",
});
});
it("accepts unzip on non-Windows hosts", async () => {
const { checkArchiveExtractor } = await import("./doctor.js");
expect(checkArchiveExtractor("darwin", (command) => command === "unzip")).toEqual({
ok: true,
detail: "unzip",
});
});
it("uses the built-in Windows extraction path", async () => {
const { checkArchiveExtractor } = await import("./doctor.js");
expect(checkArchiveExtractor("win32", () => false)).toEqual({
ok: true,
detail: "Built into Windows",
});
});
});
describe("buildDoctorReport", () => {
it("emits the locked schema shape", () => {
const report = buildDoctorReport(OUTCOMES_ALL_OK);
+33 -1
View File
@@ -1,6 +1,6 @@
// fallow-ignore-file complexity
import { defineCommand } from "citty";
import { execSync } from "node:child_process";
import { execFileSync, execSync } from "node:child_process";
import { platform } from "node:os";
import type { Example } from "./_examples.js";
import { c } from "../ui/colors.js";
@@ -133,6 +133,37 @@ function checkDisk(): CheckResult {
return { ok: true, detail: `${freeGb} GB free` };
}
function commandExists(command: string): boolean {
try {
execFileSync("which", [command], { stdio: "ignore", timeout: 5000 });
return true;
} catch {
return false;
}
}
/**
* Puppeteer's managed Chrome download delegates ZIP extraction to `unzip` on
* macOS and Linux. Windows has built-in tar/PowerShell extraction paths, so it
* does not need this Unix dependency.
*/
export function checkArchiveExtractor(
hostPlatform = platform(),
exists: (command: string) => boolean = commandExists,
): CheckResult {
if (hostPlatform === "win32") {
return { ok: true, detail: "Built into Windows" };
}
if (exists("unzip")) {
return { ok: true, detail: "unzip" };
}
return {
ok: false,
detail: "Not found",
hint: "Install unzip so HyperFrames can extract its managed Chrome download.",
};
}
function checkEnvironment(): CheckResult {
const sys = getSystemMeta();
const parts: string[] = [];
@@ -238,6 +269,7 @@ export default defineCommand({
{ name: "CPU", run: checkCPU },
{ name: "Memory", run: checkMemory },
{ name: "Disk", run: checkDisk },
{ name: "Archive extractor", run: checkArchiveExtractor },
];
// /dev/shm is only relevant on Linux (especially Docker)