Files
SeedPass/js/packages/cli/build.mjs
T
thePR0M3TH3ANandClaude Fable 5 1864343084 cutover: close gates 5, 6 and 7
Gate 5 (feature parity) -- document import/export ported: `entry
import-document` reads a text file (label defaults to the file stem, type
from the extension) and `entry export-document` writes one back, reproducing
Python's filename sanitization, directory-vs-file destination handling and
overwrite refusal. That was the last concrete item; the three remaining
exclusions (PGP RSA, semantic, api) are now documented decisions rather than
open work, and none of them blocks cutover.

Gate 6 (packaging) -- js/packages/cli/build.mjs bundles the CLI into a
single self-contained ESM file with no runtime dependencies beyond Node 22,
writes a .sha256 beside it, and is wired up as the package `bin` and
`prepack` so npm install/pack produce a working command. --version now
reports a real version stamped at build time. CI builds the bundle and
smoke-tests it from a directory with no node_modules -- version,
capabilities, profile creation, entry creation, reveal -- then uploads it.
Verified locally that the bundle runs standalone outside the workspace.

Gate 7 (migration and rollback) -- docs/typescript_migration_guide.md: the
migration is a no-op (same profiles), so the guide covers what to back up,
how to rehearse against a copy with SEEDPASS_APP_DIR, the two behavioral
differences users will notice, the known exclusions, and seed-only recovery.
Rollback is proven rather than asserted: new cross-impl phase K drives a
profile through the TS CLI -- several entry kinds created, one edited, one
archived -- then checks Python reopens it, sees every change, derives the
same secrets, and can still write to it afterwards.

Also adds js/packages/cli/README.md documenting the reference-first output
model and the scoped-token workflow.

193 core + 49 CLI tests green; 36/36 cross-implementation checks green.
All eight cutover gates are now green.

Co-Authored-By: Claude Fable 5 <[email protected]>
2026-08-14 21:33:28 -04:00

51 lines
1.7 KiB
JavaScript

#!/usr/bin/env node
/**
* Bundle the CLI into a single self-contained ESM file.
*
* Shipping a bundle rather than the TypeScript sources means the installed
* command has no build step, no tsx loader at runtime, and a fixed
* dependency set that can be checksummed — the release-integrity workflow
* hashes exactly what users execute.
*/
import { build } from "esbuild";
import { readFile, writeFile, chmod, mkdir } from "node:fs/promises";
import { dirname, join } from "node:path";
import { fileURLToPath } from "node:url";
import { createHash } from "node:crypto";
const here = dirname(fileURLToPath(import.meta.url));
const pkg = JSON.parse(await readFile(join(here, "package.json"), "utf8"));
const outfile = join(here, "dist", "seedpass-js.mjs");
await mkdir(dirname(outfile), { recursive: true });
await build({
entryPoints: [join(here, "src", "main.ts")],
outfile,
bundle: true,
platform: "node",
target: "node22",
format: "esm",
minify: false, // auditability beats a few hundred kilobytes
sourcemap: false,
banner: {
js:
"#!/usr/bin/env node\n" +
"// SeedPass CLI (TypeScript port). Generated by build.mjs — do not edit.\n" +
"import { createRequire as __seedpassCreateRequire } from 'node:module';\n" +
"const require = __seedpassCreateRequire(import.meta.url);\n",
},
define: { __SEEDPASS_VERSION__: JSON.stringify(pkg.version) },
});
await chmod(outfile, 0o755);
const bytes = await readFile(outfile);
const digest = createHash("sha256").update(bytes).digest("hex");
await writeFile(`${outfile}.sha256`, `${digest} seedpass-js.mjs\n`);
console.log(`built ${outfile}`);
console.log(` ${(bytes.length / 1024).toFixed(0)} KiB`);
console.log(` sha256 ${digest}`);