#!/usr/bin/env node // backfill-toc.mjs — Fase 1b applier: insert a `## Innhold` TOC into EXISTING large // reference files via transform.insertToc. Dry-run by default; --write applies in place. // // transform.mjs stays pure (it never writes — architecture invariant); THIS script is // the operator-gate-side applier, the same seam commands/kb-update.md occupies when it // writes a composed file after the gate clears. All the logic lives in the tested // insertToc (no-op on small/already-TOC'd files, body byte-identical) — this is glue. // // node scripts/kb-update/backfill-toc.mjs # dry-run (report) // node scripts/kb-update/backfill-toc.mjs --write # apply in place // // Per file: would/write (+N lines, M sections) | skip (small or already has TOC). // A file whose content insertToc leaves unchanged is never rewritten (no churn). import { readFileSync, writeFileSync } from 'node:fs'; import { insertToc, buildToc } from './lib/transform.mjs'; const argv = process.argv.slice(2); const write = argv.includes('--write'); const files = argv.filter((a) => a !== '--write'); if (files.length === 0) { console.error('usage: backfill-toc.mjs [--write] '); process.exit(2); } let changed = 0; let skipped = 0; for (const path of files) { const before = readFileSync(path, 'utf8'); const after = insertToc(before); if (after === before) { skipped++; console.log(`skip ${path} (small or already has TOC)`); continue; } const addedLines = after.split('\n').length - before.split('\n').length; const sections = (buildToc(before).match(/^- /gm) || []).length; changed++; if (write) { writeFileSync(path, after); console.log(`write ${path} (+${addedLines} lines, ${sections} sections)`); } else { console.log(`would ${path} (+${addedLines} lines, ${sections} sections)`); } } const verb = write ? 'wrote' : 'would change'; const hint = write ? '' : ' — re-run with --write to apply'; console.log(`\n${verb} ${changed}, skipped ${skipped}${hint}`);