memoir-cli 3.0.0 → 3.0.1

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/bin/memoir.js CHANGED
@@ -239,9 +239,8 @@ program
239
239
  console.log('\n' + chalk.cyan(`Updating memoir ${VERSION} → ${chalk.green.bold(latest)}...`) + '\n');
240
240
 
241
241
  const { execSync } = await import('child_process');
242
- const execPath = process.argv[1] || '';
243
- const useBun = execPath.includes('.bun') || process.env.BUN_INSTALL;
244
- const cmd = useBun ? 'bun install -g memoir-cli' : 'npm install -g memoir-cli';
242
+ // Always use npm bun installs to a different location and can cause PATH conflicts
243
+ const cmd = 'npm install -g memoir-cli';
245
244
 
246
245
  execSync(cmd, { stdio: 'inherit' });
247
246
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "memoir-cli",
3
- "version": "3.0.0",
3
+ "version": "3.0.1",
4
4
  "description": "Sync AI memory across devices. Back up and restore Claude, Gemini, Codex, Cursor, Copilot, Windsurf configs. Snapshot coding sessions and resume on another machine. Migrate instructions between AI assistants.",
5
5
  "main": "src/index.js",
6
6
  "type": "module",
@@ -9,7 +9,7 @@ import { adapters } from '../adapters/index.js';
9
9
  // on this machine, rather than trying to compute the encoding ourselves.
10
10
  // Claude's path encoding varies across platforms and versions, so detection
11
11
  // is the only reliable approach.
12
- function detectLocalHomeKey(adapterSource) {
12
+ export function detectLocalHomeKey(adapterSource) {
13
13
  const localProjectsDir = path.join(adapterSource, 'projects');
14
14
  if (!fs.existsSync(localProjectsDir)) return null;
15
15
 
@@ -65,7 +65,14 @@ function remapProjectPaths(backupDir, adapterSource) {
65
65
  if (!localHomeKey) {
66
66
  const home = os.homedir();
67
67
  // Use the same encoding Claude uses: path with separators → dashes
68
- localHomeKey = '-' + home.replace(/^\//, '').replace(/\\/g, '-').replace(/\//g, '-').replace(/:/g, '');
68
+ // Claude encodes paths: each separator (/ \ :) → dash
69
+ // macOS /Users/cam → -Users-cam (leading / stripped, prefixed with -)
70
+ // Windows C:\Users\X → C--Users-X (C + dash for colon + dash for backslash)
71
+ if (process.platform === 'win32') {
72
+ localHomeKey = home.replace(/\\/g, '-').replace(/:/g, '-');
73
+ } else {
74
+ localHomeKey = '-' + home.replace(/^\//, '').replace(/\//g, '-');
75
+ }
69
76
  }
70
77
 
71
78
  // Step 3: Identify foreign home keys in the backup
@@ -9,6 +9,7 @@ import inquirer from 'inquirer';
9
9
  import { getConfig } from '../config.js';
10
10
  import { fetchFromLocal, fetchFromGit } from '../providers/restore.js';
11
11
  import { decryptDirectory, verifyPassphrase } from '../security/encryption.js';
12
+ import { detectLocalHomeKey } from '../adapters/restore.js';
12
13
 
13
14
  const home = os.homedir();
14
15
 
@@ -135,9 +136,19 @@ export async function restoreCommand(options = {}) {
135
136
  await fs.writeFile(path.join(localHandoffDir, 'latest.md'), handoffContent);
136
137
 
137
138
  // Inject into Claude's home-level memory so it's always loaded
138
- const cwdKey = '-' + home.replace(/^\//, '').replace(/\\/g, '-').replace(/\//g, '-').replace(/:/g, '');
139
- const claudeMemDir = path.join(home, '.claude', 'projects', cwdKey, 'memory');
140
- if (await fs.pathExists(path.join(home, '.claude'))) {
139
+ // Use detection (reads what Claude actually created) with corrected fallback
140
+ const claudeDir = path.join(home, '.claude');
141
+ if (await fs.pathExists(claudeDir)) {
142
+ let homeKey = detectLocalHomeKey(claudeDir);
143
+ if (!homeKey) {
144
+ // Fallback: compute key matching Claude's actual encoding
145
+ if (process.platform === 'win32') {
146
+ homeKey = home.replace(/\\/g, '-').replace(/:/g, '-');
147
+ } else {
148
+ homeKey = '-' + home.replace(/^\//, '').replace(/\//g, '-');
149
+ }
150
+ }
151
+ const claudeMemDir = path.join(claudeDir, 'projects', homeKey, 'memory');
141
152
  await fs.ensureDir(claudeMemDir);
142
153
  await fs.writeFile(path.join(claudeMemDir, 'handoff.md'), handoffContent);
143
154
  handoffInjected = true;
@@ -51,7 +51,13 @@ async function injectHandoff(content, tool) {
51
51
  claude: () => {
52
52
  // Write to Claude's project memory dir so it's auto-loaded
53
53
  const cwd = process.cwd();
54
- const cwdKey = '-' + cwd.replace(/^\//, '').replace(/\\/g, '-').replace(/\//g, '-').replace(/:/g, '');
54
+ // Match Claude's actual path encoding: each separator → dash
55
+ let cwdKey;
56
+ if (process.platform === 'win32') {
57
+ cwdKey = cwd.replace(/\\/g, '-').replace(/:/g, '-');
58
+ } else {
59
+ cwdKey = '-' + cwd.replace(/^\//, '').replace(/\//g, '-');
60
+ }
55
61
  const memDir = path.join(home, '.claude', 'projects', cwdKey, 'memory');
56
62
  return path.join(memDir, 'handoff.md');
57
63
  },