diff --git a/Releases/v4.0.3/.claude/PAI/Tools/ActivityParser.ts b/Releases/v4.0.3/.claude/PAI/Tools/ActivityParser.ts index eaf399abb..ae0901929 100755 --- a/Releases/v4.0.3/.claude/PAI/Tools/ActivityParser.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/ActivityParser.ts @@ -21,7 +21,7 @@ import * as path from "path"; // Configuration // ============================================================================ -const CLAUDE_DIR = path.join(process.env.HOME!, ".claude"); +const CLAUDE_DIR = process.env.PAI_DIR || path.join(process.env.HOME!, ".claude"); const MEMORY_DIR = path.join(CLAUDE_DIR, "MEMORY"); const USERNAME = process.env.USER || require("os").userInfo().username; const PROJECTS_DIR = path.join(CLAUDE_DIR, "projects", `-Users-${USERNAME}--claude`); // Claude Code native storage diff --git a/Releases/v4.0.3/.claude/PAI/Tools/AlgorithmPhaseReport.ts b/Releases/v4.0.3/.claude/PAI/Tools/AlgorithmPhaseReport.ts index 5aa21aec0..9c43b04f2 100644 --- a/Releases/v4.0.3/.claude/PAI/Tools/AlgorithmPhaseReport.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/AlgorithmPhaseReport.ts @@ -15,7 +15,8 @@ import { join } from "path"; import { homedir } from "os"; import { parseArgs } from "util"; -const STATE_DIR = join(homedir(), ".claude", "MEMORY", "STATE"); +const PAI_DIR = process.env.PAI_DIR || join(homedir(), ".claude"); +const STATE_DIR = join(PAI_DIR, "MEMORY", "STATE"); const STATE_FILE = join(STATE_DIR, "algorithm-phase.json"); interface AlgorithmState { diff --git a/Releases/v4.0.3/.claude/PAI/Tools/Banner.ts b/Releases/v4.0.3/.claude/PAI/Tools/Banner.ts index 796fccb5a..c17791446 100755 --- a/Releases/v4.0.3/.claude/PAI/Tools/Banner.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/Banner.ts @@ -13,7 +13,7 @@ import { join } from "path"; import { spawnSync } from "child_process"; const HOME = process.env.HOME!; -const CLAUDE_DIR = join(HOME, ".claude"); +const CLAUDE_DIR = process.env.PAI_DIR || join(HOME, ".claude"); // ═══════════════════════════════════════════════════════════════════════════ // Terminal Width Detection diff --git a/Releases/v4.0.3/.claude/PAI/Tools/BannerMatrix.ts b/Releases/v4.0.3/.claude/PAI/Tools/BannerMatrix.ts index d66ada3f6..4e76557b6 100755 --- a/Releases/v4.0.3/.claude/PAI/Tools/BannerMatrix.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/BannerMatrix.ts @@ -22,7 +22,7 @@ import { join } from "path"; import { spawnSync } from "child_process"; const HOME = process.env.HOME!; -const CLAUDE_DIR = join(HOME, ".claude"); +const CLAUDE_DIR = process.env.PAI_DIR || join(HOME, ".claude"); // ============================================================================= // Terminal Width Detection diff --git a/Releases/v4.0.3/.claude/PAI/Tools/BannerNeofetch.ts b/Releases/v4.0.3/.claude/PAI/Tools/BannerNeofetch.ts index dc546829c..844daa954 100755 --- a/Releases/v4.0.3/.claude/PAI/Tools/BannerNeofetch.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/BannerNeofetch.ts @@ -15,7 +15,7 @@ import { join } from "path"; import { spawnSync } from "child_process"; const HOME = process.env.HOME!; -const CLAUDE_DIR = join(HOME, ".claude"); +const CLAUDE_DIR = process.env.PAI_DIR || join(HOME, ".claude"); // ═══════════════════════════════════════════════════════════════════════ // Terminal Width Detection diff --git a/Releases/v4.0.3/.claude/PAI/Tools/BannerRetro.ts b/Releases/v4.0.3/.claude/PAI/Tools/BannerRetro.ts index d36511091..3b604261f 100755 --- a/Releases/v4.0.3/.claude/PAI/Tools/BannerRetro.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/BannerRetro.ts @@ -20,7 +20,7 @@ import { join } from "path"; import { spawnSync } from "child_process"; const HOME = process.env.HOME!; -const CLAUDE_DIR = join(HOME, ".claude"); +const CLAUDE_DIR = process.env.PAI_DIR || join(HOME, ".claude"); // ═══════════════════════════════════════════════════════════════════════════ // Terminal Width Detection diff --git a/Releases/v4.0.3/.claude/PAI/Tools/BuildCLAUDE.ts b/Releases/v4.0.3/.claude/PAI/Tools/BuildCLAUDE.ts index 03db9799b..ef45e191e 100644 --- a/Releases/v4.0.3/.claude/PAI/Tools/BuildCLAUDE.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/BuildCLAUDE.ts @@ -15,9 +15,9 @@ import { readFileSync, writeFileSync, existsSync } from "fs"; import { join } from "path"; -const PAI_DIR = join(process.env.HOME!, ".claude"); +const PAI_DIR = process.env.PAI_DIR || join(process.env.HOME!, ".claude"); const TEMPLATE_PATH = join(PAI_DIR, "CLAUDE.md.template"); -const OUTPUT_PATH = join(PAI_DIR, "CLAUDE.md"); +const OUTPUT_PATH = join(process.env.HOME!, ".claude", "CLAUDE.md"); // Always ~/.claude/ — Claude Code reads from fixed location const SETTINGS_PATH = join(PAI_DIR, "settings.json"); const ALGORITHM_DIR = join(PAI_DIR, "PAI/Algorithm"); const LATEST_PATH = join(ALGORITHM_DIR, "LATEST"); diff --git a/Releases/v4.0.3/.claude/PAI/Tools/FeatureRegistry.ts b/Releases/v4.0.3/.claude/PAI/Tools/FeatureRegistry.ts index 83c435633..7384bce7b 100755 --- a/Releases/v4.0.3/.claude/PAI/Tools/FeatureRegistry.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/FeatureRegistry.ts @@ -55,7 +55,8 @@ interface FeatureRegistry { }; } -const REGISTRY_DIR = join(process.env.HOME || '', '.claude', 'MEMORY', 'progress'); +const PAI_DIR = process.env.PAI_DIR || join(process.env.HOME || '', '.claude'); +const REGISTRY_DIR = join(PAI_DIR, 'MEMORY', 'progress'); function getRegistryPath(project: string): string { return join(REGISTRY_DIR, `${project}-features.json`); diff --git a/Releases/v4.0.3/.claude/PAI/Tools/LearningPatternSynthesis.ts b/Releases/v4.0.3/.claude/PAI/Tools/LearningPatternSynthesis.ts index a135aaab0..9676dfc5a 100755 --- a/Releases/v4.0.3/.claude/PAI/Tools/LearningPatternSynthesis.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/LearningPatternSynthesis.ts @@ -24,7 +24,7 @@ import * as path from "path"; // Configuration // ============================================================================ -const CLAUDE_DIR = path.join(process.env.HOME!, ".claude"); +const CLAUDE_DIR = process.env.PAI_DIR || path.join(process.env.HOME!, ".claude"); const LEARNING_DIR = path.join(CLAUDE_DIR, "MEMORY", "LEARNING"); const RATINGS_FILE = path.join(LEARNING_DIR, "SIGNALS", "ratings.jsonl"); const SYNTHESIS_DIR = path.join(LEARNING_DIR, "SYNTHESIS"); diff --git a/Releases/v4.0.3/.claude/PAI/Tools/LoadSkillConfig.ts b/Releases/v4.0.3/.claude/PAI/Tools/LoadSkillConfig.ts index 1f164ff9d..225f979b5 100755 --- a/Releases/v4.0.3/.claude/PAI/Tools/LoadSkillConfig.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/LoadSkillConfig.ts @@ -35,7 +35,8 @@ interface ExtendManifest { // Constants const HOME = homedir(); -const CUSTOMIZATION_DIR = join(HOME, '.claude', 'PAI', 'USER', 'SKILLCUSTOMIZATIONS'); +const PAI_DIR = process.env.PAI_DIR || join(HOME, '.claude'); +const CUSTOMIZATION_DIR = join(PAI_DIR, 'PAI', 'USER', 'SKILLCUSTOMIZATIONS'); /** * Deep merge two objects recursively diff --git a/Releases/v4.0.3/.claude/PAI/Tools/NeofetchBanner.ts b/Releases/v4.0.3/.claude/PAI/Tools/NeofetchBanner.ts index b8ef9832f..31abbf6ba 100755 --- a/Releases/v4.0.3/.claude/PAI/Tools/NeofetchBanner.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/NeofetchBanner.ts @@ -20,7 +20,7 @@ import { join } from "path"; import { spawnSync } from "child_process"; const HOME = process.env.HOME!; -const CLAUDE_DIR = join(HOME, ".claude"); +const CLAUDE_DIR = process.env.PAI_DIR || join(HOME, ".claude"); // ═══════════════════════════════════════════════════════════════════════ // Terminal Width Detection diff --git a/Releases/v4.0.3/.claude/PAI/Tools/RebuildPAI.ts b/Releases/v4.0.3/.claude/PAI/Tools/RebuildPAI.ts index f31b11e48..8fb95f147 100755 --- a/Releases/v4.0.3/.claude/PAI/Tools/RebuildPAI.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/RebuildPAI.ts @@ -13,11 +13,12 @@ import { readdirSync, readFileSync, writeFileSync } from "fs"; import { join } from "path"; const HOME = process.env.HOME!; -const PAI_DIR = join(HOME, ".claude/PAI"); +const CLAUDE_DIR = process.env.PAI_DIR || join(HOME, ".claude"); +const PAI_DIR = join(CLAUDE_DIR, "PAI"); const COMPONENTS_DIR = join(PAI_DIR, "Components"); const ALGORITHM_DIR = join(COMPONENTS_DIR, "Algorithm"); const OUTPUT_FILE = join(PAI_DIR, "SKILL.md"); -const SETTINGS_PATH = join(HOME, ".claude/settings.json"); +const SETTINGS_PATH = join(CLAUDE_DIR, "settings.json"); /** * Load identity variables from settings.json for template resolution diff --git a/Releases/v4.0.3/.claude/PAI/Tools/SessionHarvester.ts b/Releases/v4.0.3/.claude/PAI/Tools/SessionHarvester.ts index 5b29cb015..2692491b7 100755 --- a/Releases/v4.0.3/.claude/PAI/Tools/SessionHarvester.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/SessionHarvester.ts @@ -25,7 +25,7 @@ import { getLearningCategory, isLearningCapture } from "../../hooks/lib/learning // Configuration // ============================================================================ -const CLAUDE_DIR = path.join(process.env.HOME!, ".claude"); +const CLAUDE_DIR = process.env.PAI_DIR || path.join(process.env.HOME!, ".claude"); // Derive the project slug dynamically from CLAUDE_DIR (works on macOS and Linux) // macOS: ${HOME}/.claude → -Users-username--claude // Linux: /home/username/.claude → -home-username--claude diff --git a/Releases/v4.0.3/.claude/PAI/Tools/SessionProgress.ts b/Releases/v4.0.3/.claude/PAI/Tools/SessionProgress.ts index 671ee35f0..2bae6bdd5 100755 --- a/Releases/v4.0.3/.claude/PAI/Tools/SessionProgress.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/SessionProgress.ts @@ -44,7 +44,8 @@ interface SessionProgress { } // Progress files are now in STATE/progress/ (consolidated from MEMORY/PROGRESS/) -const PROGRESS_DIR = join(process.env.HOME || '', '.claude', 'MEMORY', 'STATE', 'progress'); +const PAI_DIR = process.env.PAI_DIR || join(process.env.HOME || '', '.claude'); +const PROGRESS_DIR = join(PAI_DIR, 'MEMORY', 'STATE', 'progress'); function getProgressPath(project: string): string { return join(PROGRESS_DIR, `${project}-progress.json`); diff --git a/Releases/v4.0.3/.claude/PAI/Tools/pai.ts b/Releases/v4.0.3/.claude/PAI/Tools/pai.ts index 67da38499..411e8af81 100755 --- a/Releases/v4.0.3/.claude/PAI/Tools/pai.ts +++ b/Releases/v4.0.3/.claude/PAI/Tools/pai.ts @@ -28,7 +28,7 @@ import { join, basename } from "path"; // Configuration // ============================================================================ -const CLAUDE_DIR = join(homedir(), ".claude"); +const CLAUDE_DIR = process.env.PAI_DIR || join(homedir(), ".claude"); const MCP_DIR = join(CLAUDE_DIR, "MCPs"); const ACTIVE_MCP = join(CLAUDE_DIR, ".mcp.json"); const BANNER_SCRIPT = join(CLAUDE_DIR, "PAI", "Tools", "Banner.ts"); diff --git a/Releases/v4.0.3/.claude/hooks/LastResponseCache.hook.ts b/Releases/v4.0.3/.claude/hooks/LastResponseCache.hook.ts index ea059de0c..1d126a6d2 100755 --- a/Releases/v4.0.3/.claude/hooks/LastResponseCache.hook.ts +++ b/Releases/v4.0.3/.claude/hooks/LastResponseCache.hook.ts @@ -12,9 +12,9 @@ */ import { readHookInput, parseTranscriptFromInput } from './lib/hook-io'; +import { getPaiDir } from './lib/paths'; import { writeFileSync } from 'fs'; import { join } from 'path'; -import { homedir } from 'os'; async function main() { const input = await readHookInput(); @@ -29,8 +29,7 @@ async function main() { if (lastResponse) { try { - const paiDir = process.env.PAI_DIR || join(homedir(), '.claude'); - const cachePath = join(paiDir, 'MEMORY', 'STATE', 'last-response.txt'); + const cachePath = join(getPaiDir(), 'MEMORY', 'STATE', 'last-response.txt'); writeFileSync(cachePath, lastResponse.slice(0, 2000), 'utf-8'); } catch (err) { console.error('[LastResponseCache] Failed to write:', err); diff --git a/Releases/v4.0.3/.claude/hooks/RatingCapture.hook.ts b/Releases/v4.0.3/.claude/hooks/RatingCapture.hook.ts index 38c7a60b6..d41299b09 100755 --- a/Releases/v4.0.3/.claude/hooks/RatingCapture.hook.ts +++ b/Releases/v4.0.3/.claude/hooks/RatingCapture.hook.ts @@ -30,6 +30,7 @@ import { appendFileSync, mkdirSync, existsSync, readFileSync, writeFileSync } from 'fs'; import { join } from 'path'; +import { getPaiDir } from './lib/paths'; import { inference } from '../PAI/Tools/Inference'; import { getIdentity, getPrincipal, getPrincipalName } from './lib/identity'; import { getLearningCategory } from './lib/learning-utils'; @@ -60,7 +61,7 @@ interface RatingEntry { // ── Shared Constants ── -const BASE_DIR = process.env.PAI_DIR || join(process.env.HOME!, '.claude'); +const BASE_DIR = getPaiDir(); const SIGNALS_DIR = join(BASE_DIR, 'MEMORY', 'LEARNING', 'SIGNALS'); const RATINGS_FILE = join(SIGNALS_DIR, 'ratings.jsonl'); const LAST_RESPONSE_CACHE = join(BASE_DIR, 'MEMORY', 'STATE', 'last-response.txt'); diff --git a/Releases/v4.0.3/.claude/hooks/SessionCleanup.hook.ts b/Releases/v4.0.3/.claude/hooks/SessionCleanup.hook.ts index 8a554a5ad..37fb8ac76 100755 --- a/Releases/v4.0.3/.claude/hooks/SessionCleanup.hook.ts +++ b/Releases/v4.0.3/.claude/hooks/SessionCleanup.hook.ts @@ -35,10 +35,11 @@ import { writeFileSync, existsSync, readFileSync, unlinkSync } from 'fs'; import { join } from 'path'; +import { getPaiDir } from './lib/paths'; import { getISOTimestamp } from './lib/time'; import { setTabState, cleanupKittySession } from './lib/tab-setter'; -const BASE_DIR = process.env.PAI_DIR || join(process.env.HOME!, '.claude'); +const BASE_DIR = getPaiDir(); const MEMORY_DIR = join(BASE_DIR, 'MEMORY'); const STATE_DIR = join(MEMORY_DIR, 'STATE'); const WORK_DIR = join(MEMORY_DIR, 'WORK'); diff --git a/Releases/v4.0.3/.claude/hooks/WorkCompletionLearning.hook.ts b/Releases/v4.0.3/.claude/hooks/WorkCompletionLearning.hook.ts index f15038fb7..f3c66e571 100755 --- a/Releases/v4.0.3/.claude/hooks/WorkCompletionLearning.hook.ts +++ b/Releases/v4.0.3/.claude/hooks/WorkCompletionLearning.hook.ts @@ -51,10 +51,11 @@ import { writeFileSync, existsSync, readFileSync, mkdirSync } from 'fs'; import { join, dirname } from 'path'; +import { getPaiDir } from './lib/paths'; import { getISOTimestamp, getPSTDate } from './lib/time'; import { getLearningCategory } from './lib/learning-utils'; -const BASE_DIR = process.env.PAI_DIR || join(process.env.HOME!, '.claude'); +const BASE_DIR = getPaiDir(); const MEMORY_DIR = join(BASE_DIR, 'MEMORY'); const STATE_DIR = join(MEMORY_DIR, 'STATE'); const WORK_DIR = join(MEMORY_DIR, 'WORK');