{"record":{"id":"e26dc187ace05e08","repo":"paperclipai/paperclip","slug":"cannot-back-up-missing-config-at-filepath","errorCode":null,"errorMessage":"Cannot back up missing config at ${filePath}","messagePattern":"Cannot back up missing config at (.+?)","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"warning","filePath":"cli/src/config/store.ts","lineNumber":170,"sourceCode":"      fs.closeSync(fileDescriptor);\n      fileDescriptor = null;\n      fs.renameSync(temporaryPath, filePath);\n      syncDirectory(path.dirname(filePath));\n      return;\n    } catch (error) {\n      if (fileDescriptor !== null) fs.closeSync(fileDescriptor);\n      fs.rmSync(temporaryPath, { force: true });\n      const code = error instanceof Error && \"code\" in error ? error.code : null;\n      if (code === \"EEXIST\") continue;\n      throw error;\n    }\n  }\n}\n\nexport function backupInvalidConfig(configPath?: string): string {\n  const filePath = resolveConfigPath(configPath);\n  if (!fs.existsSync(filePath)) {\n    throw new Error(`Cannot back up missing config at ${filePath}`);\n  }\n\n  for (let suffix = 1; ; suffix += 1) {\n    const backupPath = `${filePath}.invalid-${suffix}`;\n    try {\n      durableCopyFile(filePath, backupPath, fs.constants.COPYFILE_EXCL);\n      return backupPath;\n    } catch (error) {\n      const code = error instanceof Error && \"code\" in error ? error.code : null;\n      if (code === \"EEXIST\") continue;\n      throw error;\n    }\n  }\n}\n\nexport function writeConfig(\n  config: PaperclipConfig,\n  configPath?: string,","sourceCodeStart":152,"sourceCodeEnd":188,"githubUrl":"https://github.com/paperclipai/paperclip/blob/67001ec6eb96ae601aa27bc91d9b2415d665334a/cli/src/config/store.ts#L152-L188","documentation":"Thrown by backupInvalidConfig(configPath?) when the resolved config file path does not exist on disk (fs.existsSync returns false). The function is meant to copy a known-bad config to a .invalid-N sidecar before overwriting it, so it refuses to operate when there is nothing to copy.","triggerScenarios":"Called backupInvalidConfig() but resolveConfigPath() resolved to a path where no file exists — either because no .paperclip/config.json was found in ancestor directories and the default home path was never created, or because the caller passed an explicit configPath that points at a missing file.","commonSituations":"1) A fresh machine with no Paperclip config yet, where a code path unconditionally calls backupInvalidConfig(). 2) A race where the config was deleted between the existence check and the backup call. 3) Passing a wrong --config flag pointing at a non-existent file.","solutions":["Check the file exists before calling: only call backupInvalidConfig() when configExists(configPath) returns true, or when readConfig() threw a validation error.","If you intended to back up, confirm the resolved path (resolveConfigPath) matches where the file actually lives.","If the config genuinely does not exist yet, skip the backup step — there is nothing to preserve."],"exampleFix":"// before\nimport { backupInvalidConfig } from \"./config/store.js\";\nconst backup = backupInvalidConfig(path); // throws if file missing\n\n// after\nimport { backupInvalidConfig, configExists } from \"./config/store.js\";\nconst backup = configExists(path) ? backupInvalidConfig(path) : null;","handlingStrategy":"validation","validationCode":"import { configExists, backupInvalidConfig } from \"./config/store.js\";\n\nfunction tryBackupInvalidConfig(configPath?: string): string | null {\n  if (!configExists(configPath)) return null;\n  return backupInvalidConfig(configPath);\n}","typeGuard":"import fs from \"node:fs\";\n\nfunction configExistsAt(p: string): boolean {\n  try { return fs.statSync(p).isFile(); } catch { return false; }\n}","tryCatchPattern":"import { backupInvalidConfig } from \"./config/store.js\";\n\nlet backup;\ntry {\n  backup = backupInvalidConfig(configPath);\n} catch (err) {\n  if (err instanceof Error && err.message.startsWith(\"Cannot back up missing config\")) {\n    backup = null; // nothing to back up; proceed without\n  } else throw err;\n}","preventionTips":["Always guard backupInvalidConfig with configExists().","Only call backupInvalidConfig in the branch where readConfig threw a validation error (file exists but is invalid).","Treat a missing config as 'no backup needed', not as an error."],"tags":["config","filesystem","backup","cli"],"backgroundTag":null,"analyzedSha":"67001ec6eb96ae601aa27bc91d9b2415d665334a","analyzedAt":"2026-08-12T12:05:45.408Z","schemaVersion":2},"datasetVersion":"2026-08-12T18:17:37.767Z"}