fix: address PR review — shebang, double-escaping, data loss, uninstall scope

- Add shebang banner to NPX CLI esbuild config so npx claude-mem works
- Remove manual backslash pre-escaping in WindsurfHooksInstaller (JSON.stringify handles it)
- Scope cache deletion to claude-mem only, not entire vendor namespace
- Use getWorkerPort() in OpenCodeInstaller instead of hard-coded 37777
- Throw on corrupt JSON in readJsonSafe/readGeminiSettings/Windsurf to prevent data loss
- Fix Cursor install stub to warn instead of silently succeeding
- Fix Gemini uninstall to remove individual hooks within groups, not whole groups
- Update tests for new corrupt-file-throws behavior

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
Alex Newman
2026-04-04 13:49:14 -07:00
parent cdffdba97a
commit ae6915b88e
9 changed files with 53 additions and 61 deletions
+6 -5
View File
@@ -9,18 +9,19 @@ import { logger } from './logger.js';
/**
* Read a JSON file safely, returning a default value if the file
* does not exist or contains corrupt JSON.
* does not exist. Throws on corrupt JSON to prevent silent data loss
* when callers merge and write back.
*
* @param filePath - Absolute path to the JSON file.
* @param defaultValue - Value returned when the file is missing or unreadable.
* @returns The parsed JSON content, or `defaultValue` on failure.
* @param defaultValue - Value returned when the file is missing.
* @returns The parsed JSON content, or `defaultValue` when file is missing.
* @throws {Error} When the file exists but contains invalid JSON.
*/
export function readJsonSafe<T>(filePath: string, defaultValue: T): T {
if (!existsSync(filePath)) return defaultValue;
try {
return JSON.parse(readFileSync(filePath, 'utf-8'));
} catch (error) {
logger.error('JSON', `Corrupt JSON file, using default`, { path: filePath }, error as Error);
return defaultValue;
throw new Error(`Corrupt JSON file, refusing to overwrite: ${filePath}`);
}
}