@cleocode/cleo 2026.3.0 → 2026.3.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/mcp/index.js CHANGED
@@ -939,6 +939,65 @@ var init_node_sqlite_adapter = __esm({
939
939
  }
940
940
  });
941
941
 
942
+ // src/store/sqlite-backup.ts
943
+ import { existsSync as existsSync3, mkdirSync, readdirSync, statSync, unlinkSync } from "node:fs";
944
+ import { join as join3 } from "node:path";
945
+ function formatTimestamp(d) {
946
+ const pad = (n, len = 2) => String(n).padStart(len, "0");
947
+ return `${d.getFullYear()}${pad(d.getMonth() + 1)}${pad(d.getDate())}-${pad(d.getHours())}${pad(d.getMinutes())}${pad(d.getSeconds())}`;
948
+ }
949
+ function rotateSnapshots(backupDir) {
950
+ try {
951
+ const files = readdirSync(backupDir).filter((f) => f.match(/^tasks-\d{8}-\d{6}\.db$/)).map((f) => ({ name: f, path: join3(backupDir, f), mtimeMs: statSync(join3(backupDir, f)).mtimeMs })).sort((a, b) => a.mtimeMs - b.mtimeMs);
952
+ while (files.length >= MAX_SNAPSHOTS) {
953
+ const oldest = files.shift();
954
+ unlinkSync(oldest.path);
955
+ }
956
+ } catch {
957
+ }
958
+ }
959
+ async function vacuumIntoBackup(opts = {}) {
960
+ const now = Date.now();
961
+ if (!opts.force && now - _lastBackupEpoch < DEBOUNCE_MS) {
962
+ return;
963
+ }
964
+ try {
965
+ const cleoDir = getCleoDir(opts.cwd);
966
+ const backupDir = join3(cleoDir, "backups", "sqlite");
967
+ mkdirSync(backupDir, { recursive: true });
968
+ const db = getNativeDb();
969
+ if (!db) return;
970
+ const dest = join3(backupDir, `tasks-${formatTimestamp(/* @__PURE__ */ new Date())}.db`);
971
+ db.exec("PRAGMA wal_checkpoint(TRUNCATE)");
972
+ rotateSnapshots(backupDir);
973
+ const safeDest = dest.replace(/'/g, "''");
974
+ db.exec(`VACUUM INTO '${safeDest}'`);
975
+ _lastBackupEpoch = Date.now();
976
+ } catch {
977
+ }
978
+ }
979
+ function listSqliteBackups(cwd) {
980
+ try {
981
+ const cleoDir = getCleoDir(cwd);
982
+ const backupDir = join3(cleoDir, "backups", "sqlite");
983
+ if (!existsSync3(backupDir)) return [];
984
+ return readdirSync(backupDir).filter((f) => f.match(/^tasks-\d{8}-\d{6}\.db$/)).map((f) => ({ name: f, path: join3(backupDir, f), mtimeMs: statSync(join3(backupDir, f)).mtimeMs })).sort((a, b) => b.mtimeMs - a.mtimeMs);
985
+ } catch {
986
+ return [];
987
+ }
988
+ }
989
+ var MAX_SNAPSHOTS, DEBOUNCE_MS, _lastBackupEpoch;
990
+ var init_sqlite_backup = __esm({
991
+ "src/store/sqlite-backup.ts"() {
992
+ "use strict";
993
+ init_paths();
994
+ init_sqlite();
995
+ MAX_SNAPSHOTS = 10;
996
+ DEBOUNCE_MS = 3e4;
997
+ _lastBackupEpoch = 0;
998
+ }
999
+ });
1000
+
942
1001
  // src/store/sqlite.ts
943
1002
  var sqlite_exports = {};
944
1003
  __export(sqlite_exports, {
@@ -954,16 +1013,74 @@ __export(sqlite_exports, {
954
1013
  resolveMigrationsFolder: () => resolveMigrationsFolder,
955
1014
  schema: () => schema_exports
956
1015
  });
957
- import { existsSync as existsSync3, mkdirSync } from "node:fs";
1016
+ import { existsSync as existsSync4, mkdirSync as mkdirSync2, copyFileSync, unlinkSync as unlinkSync2, renameSync as renameSync2 } from "node:fs";
958
1017
  import { createRequire as createRequire2 } from "node:module";
959
- import { dirname as dirname2, join as join3, resolve as resolve3 } from "node:path";
1018
+ import { dirname as dirname2, join as join4, resolve as resolve3 } from "node:path";
960
1019
  import { fileURLToPath } from "node:url";
961
1020
  import { eq } from "drizzle-orm";
962
1021
  import { readMigrationFiles } from "drizzle-orm/migrator";
963
1022
  import { drizzle } from "drizzle-orm/sqlite-proxy";
964
1023
  import { migrate } from "drizzle-orm/sqlite-proxy/migrator";
965
1024
  function getDbPath(cwd) {
966
- return join3(getCleoDirAbsolute(cwd), DB_FILENAME);
1025
+ return join4(getCleoDirAbsolute(cwd), DB_FILENAME);
1026
+ }
1027
+ async function autoRecoverFromBackup(nativeDb, dbPath, cwd) {
1028
+ const log5 = getLogger("sqlite");
1029
+ try {
1030
+ const countResult = nativeDb.prepare("SELECT COUNT(*) as cnt FROM tasks").get();
1031
+ const taskCount = countResult?.cnt ?? 0;
1032
+ if (taskCount > 0) return;
1033
+ const backups = listSqliteBackups(cwd);
1034
+ if (backups.length === 0) {
1035
+ return;
1036
+ }
1037
+ const newestBackup = backups[0];
1038
+ const backupDb = new DatabaseSync2(newestBackup.path, { readOnly: true });
1039
+ let backupTaskCount = 0;
1040
+ try {
1041
+ const backupCount = backupDb.prepare("SELECT COUNT(*) as cnt FROM tasks").get();
1042
+ backupTaskCount = backupCount?.cnt ?? 0;
1043
+ } finally {
1044
+ backupDb.close();
1045
+ }
1046
+ if (backupTaskCount < MIN_BACKUP_TASK_COUNT) {
1047
+ return;
1048
+ }
1049
+ log5.warn(
1050
+ { dbPath, backupPath: newestBackup.path, backupTasks: backupTaskCount },
1051
+ `Empty database detected with ${backupTaskCount}-task backup available. Auto-recovering from backup. This likely happened because git-tracked WAL/SHM files were overwritten during a branch switch (T5188).`
1052
+ );
1053
+ nativeDb.close();
1054
+ const walPath = dbPath + "-wal";
1055
+ const shmPath = dbPath + "-shm";
1056
+ try {
1057
+ unlinkSync2(walPath);
1058
+ } catch {
1059
+ }
1060
+ try {
1061
+ unlinkSync2(shmPath);
1062
+ } catch {
1063
+ }
1064
+ const tempPath = dbPath + ".recovery-tmp";
1065
+ copyFileSync(newestBackup.path, tempPath);
1066
+ renameSync2(tempPath, dbPath);
1067
+ log5.info(
1068
+ { dbPath, backupPath: newestBackup.path, restoredTasks: backupTaskCount },
1069
+ "Database auto-recovered from backup successfully."
1070
+ );
1071
+ const restoredNativeDb = openNativeDatabase(dbPath);
1072
+ _nativeDb = restoredNativeDb;
1073
+ const callback = createDrizzleCallback(restoredNativeDb);
1074
+ const batchCb = createBatchCallback(restoredNativeDb);
1075
+ const restoredDb = drizzle(callback, batchCb, { schema: schema_exports });
1076
+ await runMigrations(restoredNativeDb, restoredDb);
1077
+ _db = restoredDb;
1078
+ } catch (err) {
1079
+ log5.error(
1080
+ { err, dbPath },
1081
+ "Auto-recovery from backup failed. Continuing with empty database."
1082
+ );
1083
+ }
967
1084
  }
968
1085
  async function getDb(cwd) {
969
1086
  const requestedPath = getDbPath(cwd);
@@ -975,7 +1092,7 @@ async function getDb(cwd) {
975
1092
  _initPromise = (async () => {
976
1093
  const dbPath = requestedPath;
977
1094
  _dbPath = dbPath;
978
- mkdirSync(dirname2(dbPath), { recursive: true });
1095
+ mkdirSync2(dirname2(dbPath), { recursive: true });
979
1096
  const nativeDb = openNativeDatabase(dbPath);
980
1097
  _nativeDb = nativeDb;
981
1098
  const callback = createDrizzleCallback(nativeDb);
@@ -988,19 +1105,28 @@ async function getDb(cwd) {
988
1105
  nativeDb.exec(
989
1106
  `INSERT OR IGNORE INTO schema_meta (key, value) VALUES ('task_id_sequence', '{"counter":0,"lastId":"T000","checksum":"seed"}')`
990
1107
  );
1108
+ await autoRecoverFromBackup(nativeDb, dbPath, cwd);
991
1109
  if (!_gitTrackingChecked) {
992
1110
  _gitTrackingChecked = true;
993
1111
  try {
994
1112
  const { execFileSync: execFileSync6 } = await import("node:child_process");
995
- execFileSync6("git", ["ls-files", "--error-unmatch", dbPath], {
996
- cwd: resolve3(dbPath, "..", ".."),
997
- stdio: "pipe"
998
- });
1113
+ const gitCwd = resolve3(dbPath, "..", "..");
1114
+ const filesToCheck = [dbPath, dbPath + "-wal", dbPath + "-shm"];
999
1115
  const log5 = getLogger("sqlite");
1000
- log5.warn(
1001
- { dbPath },
1002
- "tasks.db is tracked by project git \u2014 this risks data loss on git operations. Run: git rm --cached .cleo/tasks.db (see ADR-013)"
1003
- );
1116
+ for (const fileToCheck of filesToCheck) {
1117
+ try {
1118
+ execFileSync6("git", ["ls-files", "--error-unmatch", fileToCheck], {
1119
+ cwd: gitCwd,
1120
+ stdio: "pipe"
1121
+ });
1122
+ const basename7 = fileToCheck.split("/").pop();
1123
+ log5.warn(
1124
+ { path: fileToCheck },
1125
+ `${basename7} is tracked by project git \u2014 this risks data loss on branch switch. Run: git rm --cached ${fileToCheck.replace(gitCwd + "/", "")} (see ADR-013, T5188)`
1126
+ );
1127
+ } catch {
1128
+ }
1129
+ }
1004
1130
  } catch {
1005
1131
  }
1006
1132
  }
@@ -1016,7 +1142,7 @@ async function getDb(cwd) {
1016
1142
  function resolveMigrationsFolder() {
1017
1143
  const __filename = fileURLToPath(import.meta.url);
1018
1144
  const __dirname2 = dirname2(__filename);
1019
- return join3(__dirname2, "..", "..", "drizzle");
1145
+ return join4(__dirname2, "..", "..", "drizzle");
1020
1146
  }
1021
1147
  function tableExists(nativeDb, tableName) {
1022
1148
  const result = nativeDb.prepare(
@@ -1110,12 +1236,12 @@ async function getSchemaVersion(cwd) {
1110
1236
  return result[0]?.value ?? null;
1111
1237
  }
1112
1238
  function dbExists(cwd) {
1113
- return existsSync3(getDbPath(cwd));
1239
+ return existsSync4(getDbPath(cwd));
1114
1240
  }
1115
1241
  function getNativeDb() {
1116
1242
  return _nativeDb;
1117
1243
  }
1118
- var _require2, DatabaseSync2, DB_FILENAME, SQLITE_SCHEMA_VERSION, SCHEMA_VERSION, _db, _nativeDb, _dbPath, _initPromise, _gitTrackingChecked, MAX_MIGRATION_RETRIES, MIGRATION_RETRY_BASE_DELAY_MS, MIGRATION_RETRY_MAX_DELAY_MS;
1244
+ var _require2, DatabaseSync2, DB_FILENAME, SQLITE_SCHEMA_VERSION, SCHEMA_VERSION, _db, _nativeDb, _dbPath, _initPromise, _gitTrackingChecked, MIN_BACKUP_TASK_COUNT, MAX_MIGRATION_RETRIES, MIGRATION_RETRY_BASE_DELAY_MS, MIGRATION_RETRY_MAX_DELAY_MS;
1119
1245
  var init_sqlite = __esm({
1120
1246
  "src/store/sqlite.ts"() {
1121
1247
  "use strict";
@@ -1123,6 +1249,7 @@ var init_sqlite = __esm({
1123
1249
  init_paths();
1124
1250
  init_node_sqlite_adapter();
1125
1251
  init_logger();
1252
+ init_sqlite_backup();
1126
1253
  _require2 = createRequire2(import.meta.url);
1127
1254
  ({ DatabaseSync: DatabaseSync2 } = _require2("node:sqlite"));
1128
1255
  DB_FILENAME = "tasks.db";
@@ -1133,6 +1260,7 @@ var init_sqlite = __esm({
1133
1260
  _dbPath = null;
1134
1261
  _initPromise = null;
1135
1262
  _gitTrackingChecked = false;
1263
+ MIN_BACKUP_TASK_COUNT = 10;
1136
1264
  MAX_MIGRATION_RETRIES = 5;
1137
1265
  MIGRATION_RETRY_BASE_DELAY_MS = 100;
1138
1266
  MIGRATION_RETRY_MAX_DELAY_MS = 2e3;
@@ -1397,7 +1525,7 @@ var init_atomic = __esm({
1397
1525
 
1398
1526
  // src/store/backup.ts
1399
1527
  import { copyFile, rename as fsRename, readdir, unlink as unlink2, stat, mkdir as mkdir2 } from "node:fs/promises";
1400
- import { join as join4, basename } from "node:path";
1528
+ import { join as join5, basename } from "node:path";
1401
1529
  async function createBackup(filePath, backupDir, maxBackups = DEFAULT_MAX_BACKUPS) {
1402
1530
  try {
1403
1531
  await mkdir2(backupDir, { recursive: true });
@@ -1411,14 +1539,14 @@ async function createBackup(filePath, backupDir, maxBackups = DEFAULT_MAX_BACKUP
1411
1539
  );
1412
1540
  }
1413
1541
  for (let i = maxBackups; i >= 1; i--) {
1414
- const current = join4(backupDir, `${fileName}.${i}`);
1542
+ const current = join5(backupDir, `${fileName}.${i}`);
1415
1543
  if (i === maxBackups) {
1416
1544
  try {
1417
1545
  await unlink2(current);
1418
1546
  } catch {
1419
1547
  }
1420
1548
  } else {
1421
- const next = join4(backupDir, `${fileName}.${i + 1}`);
1549
+ const next = join5(backupDir, `${fileName}.${i + 1}`);
1422
1550
  try {
1423
1551
  await stat(current);
1424
1552
  await fsRename(current, next);
@@ -1426,7 +1554,7 @@ async function createBackup(filePath, backupDir, maxBackups = DEFAULT_MAX_BACKUP
1426
1554
  }
1427
1555
  }
1428
1556
  }
1429
- const backupPath = join4(backupDir, `${fileName}.1`);
1557
+ const backupPath = join5(backupDir, `${fileName}.1`);
1430
1558
  await copyFile(filePath, backupPath);
1431
1559
  return backupPath;
1432
1560
  } catch (err) {
@@ -2196,15 +2324,15 @@ var init_sqlite_data_accessor = __esm({
2196
2324
 
2197
2325
  // src/store/git-checkpoint.ts
2198
2326
  import { readFile as readFile2, writeFile } from "node:fs/promises";
2199
- import { existsSync as existsSync4 } from "node:fs";
2327
+ import { existsSync as existsSync5 } from "node:fs";
2200
2328
  import { execFile } from "node:child_process";
2201
2329
  import { promisify } from "node:util";
2202
- import { join as join5, resolve as resolve4 } from "node:path";
2330
+ import { join as join6, resolve as resolve4 } from "node:path";
2203
2331
  function makeCleoGitEnv(cleoDir) {
2204
2332
  const abs = resolve4(cleoDir);
2205
2333
  return {
2206
2334
  ...process.env,
2207
- GIT_DIR: join5(abs, ".git"),
2335
+ GIT_DIR: join6(abs, ".git"),
2208
2336
  GIT_WORK_TREE: abs
2209
2337
  };
2210
2338
  }
@@ -2222,7 +2350,7 @@ async function cleoGitCommand(args, cleoDir) {
2222
2350
  }
2223
2351
  }
2224
2352
  function isCleoGitInitialized(cleoDir) {
2225
- return existsSync4(join5(cleoDir, ".git", "HEAD"));
2353
+ return existsSync5(join6(cleoDir, ".git", "HEAD"));
2226
2354
  }
2227
2355
  async function loadCheckpointConfig(cwd) {
2228
2356
  try {
@@ -2249,25 +2377,25 @@ async function isCleoGitRepo(cleoDir) {
2249
2377
  return result.success && (result.stdout === "true" || isCleoGitInitialized(cleoDir));
2250
2378
  }
2251
2379
  function isMergeInProgress(cleoDir) {
2252
- return existsSync4(join5(cleoDir, ".git", "MERGE_HEAD"));
2380
+ return existsSync5(join6(cleoDir, ".git", "MERGE_HEAD"));
2253
2381
  }
2254
2382
  async function isDetachedHead(cleoDir) {
2255
2383
  const result = await cleoGitCommand(["symbolic-ref", "HEAD"], cleoDir);
2256
2384
  return !result.success;
2257
2385
  }
2258
2386
  function isRebaseInProgress(cleoDir) {
2259
- return existsSync4(join5(cleoDir, ".git", "rebase-merge")) || existsSync4(join5(cleoDir, ".git", "rebase-apply"));
2387
+ return existsSync5(join6(cleoDir, ".git", "rebase-merge")) || existsSync5(join6(cleoDir, ".git", "rebase-apply"));
2260
2388
  }
2261
2389
  async function recordCheckpointTime(cleoDir) {
2262
2390
  try {
2263
- const stateFile = join5(cleoDir, CHECKPOINT_STATE_FILE);
2391
+ const stateFile = join6(cleoDir, CHECKPOINT_STATE_FILE);
2264
2392
  await writeFile(stateFile, String(Math.floor(Date.now() / 1e3)));
2265
2393
  } catch {
2266
2394
  }
2267
2395
  }
2268
2396
  async function getLastCheckpointTime(cleoDir) {
2269
2397
  try {
2270
- const stateFile = join5(cleoDir, CHECKPOINT_STATE_FILE);
2398
+ const stateFile = join6(cleoDir, CHECKPOINT_STATE_FILE);
2271
2399
  const content = await readFile2(stateFile, "utf-8");
2272
2400
  const epoch = parseInt(content.trim(), 10);
2273
2401
  return isNaN(epoch) ? 0 : epoch;
@@ -2278,8 +2406,8 @@ async function getLastCheckpointTime(cleoDir) {
2278
2406
  async function getChangedStateFiles(cleoDir) {
2279
2407
  const changed = [];
2280
2408
  for (const stateFile of STATE_FILES) {
2281
- const fullPath = join5(cleoDir, stateFile);
2282
- if (!existsSync4(fullPath)) continue;
2409
+ const fullPath = join6(cleoDir, stateFile);
2410
+ if (!existsSync5(fullPath)) continue;
2283
2411
  const diffResult = await cleoGitCommand(["diff", "--quiet", "--", stateFile], cleoDir);
2284
2412
  const cachedResult = await cleoGitCommand(["diff", "--cached", "--quiet", "--", stateFile], cleoDir);
2285
2413
  const untrackedResult = await cleoGitCommand(
@@ -2303,7 +2431,7 @@ async function shouldCheckpoint(options) {
2303
2431
  const config = await loadCheckpointConfig(cwd);
2304
2432
  if (!config.enabled) return false;
2305
2433
  const cleoDir = getCleoDir(cwd);
2306
- if (!existsSync4(cleoDir)) return false;
2434
+ if (!existsSync5(cleoDir)) return false;
2307
2435
  if (!isCleoGitInitialized(cleoDir)) return false;
2308
2436
  if (!await isCleoGitRepo(cleoDir)) return false;
2309
2437
  if (isMergeInProgress(cleoDir)) return false;
@@ -2375,55 +2503,6 @@ var init_git_checkpoint = __esm({
2375
2503
  }
2376
2504
  });
2377
2505
 
2378
- // src/store/sqlite-backup.ts
2379
- import { existsSync as existsSync5, mkdirSync as mkdirSync2, readdirSync, statSync, unlinkSync } from "node:fs";
2380
- import { join as join6 } from "node:path";
2381
- function formatTimestamp(d) {
2382
- const pad = (n, len = 2) => String(n).padStart(len, "0");
2383
- return `${d.getFullYear()}${pad(d.getMonth() + 1)}${pad(d.getDate())}-${pad(d.getHours())}${pad(d.getMinutes())}${pad(d.getSeconds())}`;
2384
- }
2385
- function rotateSnapshots(backupDir) {
2386
- try {
2387
- const files = readdirSync(backupDir).filter((f) => f.match(/^tasks-\d{8}-\d{6}\.db$/)).map((f) => ({ name: f, path: join6(backupDir, f), mtimeMs: statSync(join6(backupDir, f)).mtimeMs })).sort((a, b) => a.mtimeMs - b.mtimeMs);
2388
- while (files.length >= MAX_SNAPSHOTS) {
2389
- const oldest = files.shift();
2390
- unlinkSync(oldest.path);
2391
- }
2392
- } catch {
2393
- }
2394
- }
2395
- async function vacuumIntoBackup(opts = {}) {
2396
- const now = Date.now();
2397
- if (!opts.force && now - _lastBackupEpoch < DEBOUNCE_MS) {
2398
- return;
2399
- }
2400
- try {
2401
- const cleoDir = getCleoDir(opts.cwd);
2402
- const backupDir = join6(cleoDir, "backups", "sqlite");
2403
- mkdirSync2(backupDir, { recursive: true });
2404
- const db = getNativeDb();
2405
- if (!db) return;
2406
- const dest = join6(backupDir, `tasks-${formatTimestamp(/* @__PURE__ */ new Date())}.db`);
2407
- db.exec("PRAGMA wal_checkpoint(TRUNCATE)");
2408
- rotateSnapshots(backupDir);
2409
- const safeDest = dest.replace(/'/g, "''");
2410
- db.exec(`VACUUM INTO '${safeDest}'`);
2411
- _lastBackupEpoch = Date.now();
2412
- } catch {
2413
- }
2414
- }
2415
- var MAX_SNAPSHOTS, DEBOUNCE_MS, _lastBackupEpoch;
2416
- var init_sqlite_backup = __esm({
2417
- "src/store/sqlite-backup.ts"() {
2418
- "use strict";
2419
- init_paths();
2420
- init_sqlite();
2421
- MAX_SNAPSHOTS = 10;
2422
- DEBOUNCE_MS = 3e4;
2423
- _lastBackupEpoch = 0;
2424
- }
2425
- });
2426
-
2427
2506
  // src/core/sequence/index.ts
2428
2507
  var sequence_exports = {};
2429
2508
  __export(sequence_exports, {
@@ -2432,7 +2511,7 @@ __export(sequence_exports, {
2432
2511
  repairSequence: () => repairSequence,
2433
2512
  showSequence: () => showSequence
2434
2513
  });
2435
- import { existsSync as existsSync6, readFileSync as readFileSync3, renameSync as renameSync2 } from "node:fs";
2514
+ import { existsSync as existsSync6, readFileSync as readFileSync3, renameSync as renameSync3 } from "node:fs";
2436
2515
  import { join as join7 } from "node:path";
2437
2516
  import { eq as eq4 } from "drizzle-orm";
2438
2517
  function getLegacySequenceJsonPath(cwd) {
@@ -2463,10 +2542,10 @@ function renameLegacyFile(path) {
2463
2542
  const migratedPath = `${path}.migrated`;
2464
2543
  try {
2465
2544
  if (!existsSync6(migratedPath)) {
2466
- renameSync2(path, migratedPath);
2545
+ renameSync3(path, migratedPath);
2467
2546
  return;
2468
2547
  }
2469
- renameSync2(path, `${migratedPath}.${Date.now()}`);
2548
+ renameSync3(path, `${migratedPath}.${Date.now()}`);
2470
2549
  } catch {
2471
2550
  }
2472
2551
  }
@@ -3028,7 +3107,7 @@ var init_data_accessor = __esm({
3028
3107
  });
3029
3108
 
3030
3109
  // src/store/file-utils.ts
3031
- import { readFileSync as readFileSync4, writeFileSync, renameSync as renameSync3, existsSync as existsSync8, unlinkSync as unlinkSync2, mkdirSync as mkdirSync3, readdirSync as readdirSync2 } from "node:fs";
3110
+ import { readFileSync as readFileSync4, writeFileSync, renameSync as renameSync4, existsSync as existsSync8, unlinkSync as unlinkSync3, mkdirSync as mkdirSync3, readdirSync as readdirSync2 } from "node:fs";
3032
3111
  import { join as join8, dirname as dirname5, basename as basename2 } from "node:path";
3033
3112
  import { randomBytes as randomBytes2 } from "node:crypto";
3034
3113
  import * as lockfile2 from "proper-lockfile";
@@ -3043,13 +3122,13 @@ function rotateBackup(filePath) {
3043
3122
  const current = join8(backupDir, `${name}.${i}`);
3044
3123
  if (i === MAX_BACKUPS) {
3045
3124
  try {
3046
- unlinkSync2(current);
3125
+ unlinkSync3(current);
3047
3126
  } catch {
3048
3127
  }
3049
3128
  } else {
3050
3129
  const next = join8(backupDir, `${name}.${i + 1}`);
3051
3130
  try {
3052
- if (existsSync8(current)) renameSync3(current, next);
3131
+ if (existsSync8(current)) renameSync4(current, next);
3053
3132
  } catch {
3054
3133
  }
3055
3134
  }
@@ -3069,10 +3148,10 @@ function writeJsonFileAtomic(filePath, data, indent = 2) {
3069
3148
  if (existsSync8(filePath)) {
3070
3149
  rotateBackup(filePath);
3071
3150
  }
3072
- renameSync3(tempPath, filePath);
3151
+ renameSync4(tempPath, filePath);
3073
3152
  } catch (error) {
3074
3153
  try {
3075
- unlinkSync2(tempPath);
3154
+ unlinkSync3(tempPath);
3076
3155
  } catch {
3077
3156
  }
3078
3157
  throw error;
@@ -12761,7 +12840,7 @@ import {
12761
12840
  writeFileSync as writeFileSync2,
12762
12841
  mkdirSync as mkdirSync6,
12763
12842
  readdirSync as readdirSync3,
12764
- copyFileSync,
12843
+ copyFileSync as copyFileSync2,
12765
12844
  statSync as statSync3,
12766
12845
  rmSync
12767
12846
  } from "node:fs";
@@ -12842,7 +12921,7 @@ function copyDirContents(srcDir, dstDir, manifestLines, copiedFiles) {
12842
12921
  for (const sf of readdirSync3(srcPath)) {
12843
12922
  if (!copiedFiles.has(sf)) {
12844
12923
  try {
12845
- copyFileSync(join13(srcPath, sf), join13(dstPath, sf));
12924
+ copyFileSync2(join13(srcPath, sf), join13(dstPath, sf));
12846
12925
  copiedFiles.add(sf);
12847
12926
  count2++;
12848
12927
  } catch {
@@ -12850,7 +12929,7 @@ function copyDirContents(srcDir, dstDir, manifestLines, copiedFiles) {
12850
12929
  }
12851
12930
  }
12852
12931
  } else if (!copiedFiles.has(entry)) {
12853
- copyFileSync(srcPath, dstPath);
12932
+ copyFileSync2(srcPath, dstPath);
12854
12933
  copiedFiles.add(entry);
12855
12934
  count2++;
12856
12935
  }
@@ -13159,7 +13238,7 @@ function getMigrationStatus(projectRoot, opts) {
13159
13238
  // src/core/system/cleanup.ts
13160
13239
  init_errors();
13161
13240
  init_exit_codes();
13162
- import { readFileSync as readFileSync11, writeFileSync as writeFileSync4, existsSync as existsSync17, readdirSync as readdirSync4, unlinkSync as unlinkSync3 } from "node:fs";
13241
+ import { readFileSync as readFileSync11, writeFileSync as writeFileSync4, existsSync as existsSync17, readdirSync as readdirSync4, unlinkSync as unlinkSync4 } from "node:fs";
13163
13242
  import { join as join17 } from "node:path";
13164
13243
  function cleanupSystem(projectRoot, params) {
13165
13244
  if (!params.target) {
@@ -13210,11 +13289,11 @@ function cleanupSystem(projectRoot, params) {
13210
13289
  if (params.olderThan && meta.timestamp < params.olderThan) {
13211
13290
  items.push(file.replace(".meta.json", ""));
13212
13291
  if (!dryRun) {
13213
- unlinkSync3(metaFilePath);
13292
+ unlinkSync4(metaFilePath);
13214
13293
  for (const bf of readdirSync4(fullDir)) {
13215
13294
  if (bf.includes(meta.backupId)) {
13216
13295
  try {
13217
- unlinkSync3(join17(fullDir, bf));
13296
+ unlinkSync4(join17(fullDir, bf));
13218
13297
  } catch {
13219
13298
  }
13220
13299
  }
@@ -13239,7 +13318,7 @@ function cleanupSystem(projectRoot, params) {
13239
13318
  items.push(file);
13240
13319
  if (!dryRun) {
13241
13320
  try {
13242
- unlinkSync3(join17(cleoDir, file));
13321
+ unlinkSync4(join17(cleoDir, file));
13243
13322
  } catch {
13244
13323
  }
13245
13324
  }