@accelerationguy/accel 1.0.1 → 1.0.3

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/install.js CHANGED
@@ -489,6 +489,234 @@ function deregisterHooks() {
489
489
  }
490
490
  }
491
491
 
492
+ // ─── User Data Paths (preserved during updates) ─────────────
493
+ const USER_DATA_PATTERNS = [
494
+ // Vector user config
495
+ 'modules/vector/vector.json',
496
+ 'modules/vector/.vector-template/vector.json',
497
+ 'modules/vector/sessions/',
498
+ // Momentum workspace data
499
+ 'modules/momentum/data/',
500
+ 'modules/momentum/workspace.json',
501
+ 'modules/momentum/operator.json',
502
+ // Drive project state
503
+ 'modules/drive/.drive/',
504
+ // Event bus (user's events and archive)
505
+ 'events/',
506
+ ];
507
+
508
+ function isUserData(relativePath) {
509
+ return USER_DATA_PATTERNS.some((pattern) => relativePath.startsWith(pattern));
510
+ }
511
+
512
+ // ─── Backup ─────────────────────────────────────────────────
513
+ function createBackup() {
514
+ if (!fs.existsSync(ACCEL_HOME)) return null;
515
+
516
+ const timestamp = new Date().toISOString().replace(/[:.]/g, '-').slice(0, 19);
517
+ const backupDir = path.join(os.homedir(), `.accel-backup-${timestamp}`);
518
+
519
+ copyRecursive(ACCEL_HOME, backupDir);
520
+ return backupDir;
521
+ }
522
+
523
+ // ─── Smart Update ───────────────────────────────────────────
524
+ function updateModule(moduleId) {
525
+ const mod = MODULES.find((m) => m.id === moduleId);
526
+ if (!mod) throw new Error(`Unknown module: ${moduleId}`);
527
+
528
+ const srcDir = path.join(PACKAGE_DIR, 'modules', moduleId);
529
+ const destDir = path.join(ACCEL_HOME, 'modules', moduleId);
530
+ const commandsDir = path.join(CLAUDE_HOME, 'commands', moduleId);
531
+
532
+ // Collect user data files before update
533
+ const preserved = new Map();
534
+ if (fs.existsSync(destDir)) {
535
+ collectUserData(destDir, ACCEL_HOME, preserved);
536
+ }
537
+
538
+ // Remove old module code (but we have preserved user data in memory)
539
+ if (fs.existsSync(destDir)) {
540
+ fs.rmSync(destDir, { recursive: true, force: true });
541
+ }
542
+ if (fs.existsSync(commandsDir)) {
543
+ fs.rmSync(commandsDir, { recursive: true, force: true });
544
+ }
545
+
546
+ // Install fresh module code
547
+ fs.mkdirSync(destDir, { recursive: true });
548
+ fs.mkdirSync(commandsDir, { recursive: true });
549
+ copyRecursive(srcDir, destDir);
550
+
551
+ // Copy slash commands
552
+ const cmdSrcDirs = [
553
+ 'commands', 'tasks', 'src/commands', 'src/tasks',
554
+ 'skillsmith/tasks', 'skillsmith',
555
+ 'mission-control/tasks', 'mission-control',
556
+ ];
557
+ for (const cmdDir of cmdSrcDirs) {
558
+ const cmdSrc = path.join(srcDir, cmdDir);
559
+ if (fs.existsSync(cmdSrc)) {
560
+ const entries = fs.readdirSync(cmdSrc);
561
+ for (const entry of entries) {
562
+ const entryPath = path.join(cmdSrc, entry);
563
+ if (entry.endsWith('.md') && fs.statSync(entryPath).isFile()) {
564
+ fs.copyFileSync(entryPath, path.join(commandsDir, entry));
565
+ }
566
+ }
567
+ }
568
+ }
569
+
570
+ // Restore user data on top of fresh code
571
+ let restoredCount = 0;
572
+ for (const [relativePath, content] of preserved) {
573
+ const fullPath = path.join(ACCEL_HOME, relativePath);
574
+ fs.mkdirSync(path.dirname(fullPath), { recursive: true });
575
+ fs.writeFileSync(fullPath, content);
576
+ restoredCount++;
577
+ }
578
+
579
+ // Reinstall hooks and MCP if needed
580
+ if (mod.hasHooks) {
581
+ const hooksSrc = path.join(srcDir, 'hooks');
582
+ const srcHooks = path.join(srcDir, 'src', 'hooks');
583
+ const hooksDir = fs.existsSync(hooksSrc) ? hooksSrc : fs.existsSync(srcHooks) ? srcHooks : null;
584
+ if (hooksDir) {
585
+ const hooksDest = path.join(CLAUDE_HOME, 'hooks');
586
+ fs.mkdirSync(hooksDest, { recursive: true });
587
+ copyRecursive(hooksDir, hooksDest);
588
+ }
589
+ }
590
+
591
+ if (mod.hasMcp) {
592
+ const mcpSrc = path.join(srcDir, 'mcp');
593
+ const pkgMcp = path.join(srcDir, 'src', 'packages', `momentum-mcp`);
594
+ const mcpDir = fs.existsSync(mcpSrc) ? mcpSrc : fs.existsSync(pkgMcp) ? pkgMcp : null;
595
+ if (mcpDir) {
596
+ const mcpDest = path.join(ACCEL_HOME, 'mcp', moduleId);
597
+ fs.mkdirSync(mcpDest, { recursive: true });
598
+ copyRecursive(mcpDir, mcpDest);
599
+ if (fs.existsSync(path.join(mcpDest, 'package.json'))) {
600
+ try {
601
+ execFileSync('npm', ['install', '--production', '--silent'], { cwd: mcpDest, stdio: 'pipe' });
602
+ } catch {}
603
+ }
604
+ }
605
+ }
606
+
607
+ return restoredCount;
608
+ }
609
+
610
+ function collectUserData(dir, baseDir, preserved) {
611
+ const entries = fs.readdirSync(dir, { withFileTypes: true });
612
+ for (const entry of entries) {
613
+ if (entry.name === 'node_modules' || entry.name === '.git') continue;
614
+ const fullPath = path.join(dir, entry.name);
615
+ const relativePath = path.relative(baseDir, fullPath);
616
+
617
+ if (entry.isDirectory()) {
618
+ collectUserData(fullPath, baseDir, preserved);
619
+ } else if (isUserData(relativePath)) {
620
+ preserved.set(relativePath, fs.readFileSync(fullPath));
621
+ }
622
+ }
623
+ }
624
+
625
+ async function runUpdate() {
626
+ if (!fs.existsSync(MANIFEST_PATH)) {
627
+ console.log(`\n ${c.yellow}Nothing to update. Run \`npx @accelerationguy/accel\` to install first.${c.reset}\n`);
628
+ process.exit(0);
629
+ }
630
+
631
+ const manifest = JSON.parse(fs.readFileSync(MANIFEST_PATH, 'utf8'));
632
+ const installedVersion = manifest.version;
633
+ const packageJson = JSON.parse(fs.readFileSync(path.join(PACKAGE_DIR, 'package.json'), 'utf8'));
634
+ const newVersion = packageJson.version;
635
+
636
+ console.log(`\n ${c.cyan}${c.bold}${BRAND} Update${c.reset}\n`);
637
+ console.log(` Installed: v${installedVersion}`);
638
+ console.log(` Available: v${newVersion}`);
639
+
640
+ if (installedVersion === newVersion) {
641
+ console.log(`\n ${c.green}Already up to date!${c.reset}\n`);
642
+ process.exit(0);
643
+ }
644
+
645
+ // Show what's installed
646
+ const installedModules = Object.keys(manifest.modules);
647
+ console.log(`\n Modules: ${installedModules.map((id) => {
648
+ const mod = MODULES.find((m) => m.id === id);
649
+ return mod ? mod.name : id;
650
+ }).join(', ')}`);
651
+
652
+ // Create backup
653
+ console.log(`\n ${c.dim}Creating backup...${c.reset}`);
654
+ const backupDir = createBackup();
655
+ if (backupDir) {
656
+ console.log(` ${c.green}\u2713${c.reset} Backup saved to ${backupDir}`);
657
+ }
658
+
659
+ // Update each installed module
660
+ console.log(`\n ${c.bold}Updating...${c.reset}\n`);
661
+
662
+ const updated = [];
663
+ const failed = [];
664
+ let totalPreserved = 0;
665
+
666
+ for (const modId of installedModules) {
667
+ const mod = MODULES.find((m) => m.id === modId);
668
+ if (!mod) continue;
669
+ try {
670
+ const restoredCount = updateModule(modId);
671
+ totalPreserved += restoredCount;
672
+ updated.push(modId);
673
+ const preserved = restoredCount > 0 ? ` ${c.dim}(${restoredCount} user files preserved)${c.reset}` : '';
674
+ console.log(` ${c.green}\u2713${c.reset} ${mod.name} updated${preserved}`);
675
+ } catch (e) {
676
+ failed.push({ id: modId, error: e.message });
677
+ console.log(` ${c.red}\u2717${c.reset} ${mod.name} failed: ${e.message}`);
678
+ }
679
+ }
680
+
681
+ // Update event bus schemas
682
+ setupEventBus();
683
+
684
+ // Update manifest version
685
+ if (updated.length > 0) {
686
+ manifest.version = newVersion;
687
+ manifest.updatedAt = new Date().toISOString();
688
+ manifest.previousVersion = installedVersion;
689
+ fs.writeFileSync(MANIFEST_PATH, JSON.stringify(manifest, null, 2));
690
+
691
+ // Re-register hooks and MCP (in case format changed)
692
+ registerHooks(updated);
693
+ registerMcpServers(updated);
694
+ installClaudeMdBlock();
695
+ }
696
+
697
+ // Summary
698
+ console.log('');
699
+ if (failed.length > 0) {
700
+ console.log(` ${c.yellow}${updated.length}/${installedModules.length} modules updated.${c.reset}`);
701
+ for (const f of failed) {
702
+ console.log(` ${c.red}\u2717${c.reset} ${f.id}: ${f.error}`);
703
+ }
704
+ if (backupDir) {
705
+ console.log(`\n ${c.dim}Backup at ${backupDir} — restore with: cp -R ${backupDir}/ ~/.accel/${c.reset}`);
706
+ }
707
+ } else {
708
+ console.log(` ${c.green}${c.bold}Updated ${BRAND} v${installedVersion} \u2192 v${newVersion}${c.reset}`);
709
+ if (totalPreserved > 0) {
710
+ console.log(` ${c.dim}${totalPreserved} user data files preserved (rules, workspace, configs)${c.reset}`);
711
+ }
712
+ console.log(`\n Restart Claude Code to pick up changes.`);
713
+ if (backupDir) {
714
+ console.log(` ${c.dim}Backup at ${backupDir} (safe to delete if everything works)${c.reset}`);
715
+ }
716
+ }
717
+ console.log('');
718
+ }
719
+
492
720
  // ─── Event Bus Setup ────────────────────────────────────────
493
721
  function setupEventBus() {
494
722
  const eventsDir = path.join(ACCEL_HOME, 'events');
@@ -549,6 +777,7 @@ async function main() {
549
777
  const isStatus = args.includes('status');
550
778
  const isUninstall = args.includes('uninstall');
551
779
  const isUpdate = args.includes('update');
780
+ const isBackup = args.includes('backup');
552
781
 
553
782
  if (isStatus) {
554
783
  if (!fs.existsSync(MANIFEST_PATH)) {
@@ -564,6 +793,21 @@ async function main() {
564
793
  process.exit(0);
565
794
  }
566
795
 
796
+ if (isUpdate) {
797
+ await runUpdate();
798
+ process.exit(0);
799
+ }
800
+
801
+ if (isBackup) {
802
+ if (!fs.existsSync(ACCEL_HOME)) {
803
+ console.log(`\n ${c.yellow}Nothing to back up. No Accelerate installation found.${c.reset}\n`);
804
+ process.exit(0);
805
+ }
806
+ const backupDir = createBackup();
807
+ console.log(`\n ${c.green}\u2713${c.reset} Backup created at: ${backupDir}\n`);
808
+ process.exit(0);
809
+ }
810
+
567
811
  if (isUninstall) {
568
812
  console.log(`\n ${c.yellow}Uninstalling ${BRAND}...${c.reset}`);
569
813
  if (fs.existsSync(ACCEL_HOME)) fs.rmSync(ACCEL_HOME, { recursive: true, force: true });
@@ -1,125 +1,123 @@
1
1
  <purpose>
2
- Detect all installed Mission Control frameworks, report versions, health, and identify any issues. Provides a single-glance view of what's installed and working.
2
+ Detect all installed Accelerate modules, report health, and identify issues. Single-glance view of what's installed and working.
3
3
  </purpose>
4
4
 
5
- <user-story>
6
- As a Claude Code user, I want to see what frameworks are installed and whether they're healthy, so I know if anything needs attention.
7
- </user-story>
8
-
9
5
  <when-to-use>
10
- - Checking what's currently installed in a workspace
11
- - Verifying an installation completed correctly
12
- - Diagnosing issues with framework behavior
13
- - Entry point routes here via /accel status
6
+ - Checking what's installed
7
+ - Verifying installation completed correctly
8
+ - Diagnosing module issues
14
9
  </when-to-use>
15
10
 
16
- <context>
17
- @frameworks/framework-registry.md
18
- </context>
19
-
20
11
  <steps>
21
12
 
22
- <step name="detect_installed" priority="first">
23
- Check each framework's installation state.
24
-
25
- For each of the 7 frameworks, run detection checks from the registry:
26
-
27
- **Vector:**
28
- - Global install: check `~/.vector/vector.json` exists
29
- - Hook: check `~/.claude/hooks/vector-hook.py` exists
30
- - MCP: check `.mcp.json` has `vector-mcp` entry (workspace-level)
31
- - Version: grep `VECTOR_HOOK_VERSION` from hook file
32
-
33
- **Momentum:**
34
- - Global install: check `~/.claude/momentum-framework/` exists
35
- - Workspace install: check `.accel/momentum/workspace.json` exists
36
- - Hooks wired: check `.claude/settings.json` for `.accel/momentum/hooks/` entries
37
- - MCP: check `.mcp.json` has `momentum-mcp` entry
38
- - Data surfaces: check `.accel/momentum/data/projects.json` exists
39
- - Version: read from `.accel/momentum/momentum-mcp/package.json`
40
-
41
- **Drive:**
42
- - Install: check `~/.claude/commands/drive/` exists
43
- - Framework: check `~/.claude/drive-framework/` exists
44
- - Version: check package.json or command file headers
45
-
46
- **Ignition:**
47
- - Install: check `~/.claude/commands/ignition/ignition.md` exists
48
- - Version: read frontmatter from ignition.md
49
-
50
- **Forge:**
51
- - Install: check `~/.claude/commands/forge/forge.md` exists
52
- - Specs: check `~/.claude/forge-specs/` exists
53
- - Version: read frontmatter from forge.md
54
-
55
- **Radar:**
56
- - Framework: check `~/.claude/radar/` exists
57
- - Commands: check `~/.claude/commands/radar/audit.md` exists
58
- - Tools: check `semgrep --version`, `trivy --version`, `gitleaks --version` etc.
59
- - Version: grep RADAR_VERSION or count framework files
60
-
61
- Run all checks in parallel where possible.
62
- </step>
13
+ <step name="read_manifest" priority="first">
14
+ Read the Accelerate manifest to know what's installed:
63
15
 
64
- <step name="assess_health">
65
- Evaluate health of installed frameworks.
16
+ ```bash
17
+ cat ~/.accel/manifest.json 2>/dev/null || echo "NOT_INSTALLED"
18
+ ```
19
+
20
+ If NOT_INSTALLED: tell user "Accelerate is not installed. Run `npx @accelerationguy/accel` to install." and stop.
66
21
 
67
- For each installed framework:
22
+ The manifest lists all installed modules, version, and install date.
23
+ </step>
24
+
25
+ <step name="detect_installed">
26
+ Check each module's actual state. Run ALL checks in parallel:
27
+
28
+ **Vector (Rules Engine):**
29
+ - Module files: `~/.accel/modules/vector/` exists
30
+ - User config: `~/.accel/modules/vector/vector.json` exists
31
+ - Hook: `~/.claude/hooks/vector-hook.py` exists
32
+ - Hook wired: `~/.claude/settings.json` has vector-hook.py in UserPromptSubmit hooks
33
+ - MCP: `~/.mcp.json` has `vector-mcp` entry
34
+ - Version: grep `VECTOR_HOOK_VERSION` from `~/.claude/hooks/vector-hook.py`
35
+
36
+ **Momentum (Workspace State):**
37
+ - Module files: `~/.accel/modules/momentum/` exists
38
+ - Data: `~/.accel/modules/momentum/data/` directory exists
39
+ - Hooks wired: `~/.claude/settings.json` has momentum hooks (active-hook.py, backlog-hook.py, momentum-pulse-check.py, psmm-injector.py, satellite-detection.py, operator.py, apex-insights.py)
40
+ - MCP: `~/.mcp.json` has `momentum-mcp` entry
41
+
42
+ **Drive (Dev Workflow):**
43
+ - Module files: `~/.accel/modules/drive/` exists
44
+ - Commands: `~/.claude/commands/drive/` exists
45
+ - Command count: count .md files in `~/.claude/commands/drive/`
46
+
47
+ **Ignition (Project Incubation):**
48
+ - Module files: `~/.accel/modules/ignition/` exists
49
+ - Commands: `~/.claude/commands/ignition/` exists
50
+ - Command count: count .md files in `~/.claude/commands/ignition/`
51
+
52
+ **Radar (Security Auditing):**
53
+ - Module files: `~/.accel/modules/radar/` exists
54
+ - Commands: `~/.claude/commands/radar/` exists
55
+ - External tools: `semgrep --version`, `trivy --version`, `gitleaks --version`
56
+
57
+ **Forge (Skill Builder):**
58
+ - Module files: `~/.accel/modules/forge/` exists
59
+ - Commands: `~/.claude/commands/forge/` exists
60
+
61
+ **Mission Control (Orchestrator):**
62
+ - Module files: `~/.accel/modules/mission-control/` exists
63
+ - Commands: `~/.claude/commands/mission-control/` exists
64
+ </step>
68
65
 
69
- 1. **Wiring check**: Is it properly wired? (hooks in settings, MCP in .mcp.json)
70
- 2. **File integrity**: Do expected files exist?
71
- 3. **Staleness**: When was it last modified vs the source repo?
72
- 4. **Cross-framework**: Are expected integrations present? (e.g., Drive domain in Vector)
66
+ <step name="assess_health">
67
+ For each module in the manifest:
73
68
 
74
- Health states:
75
- - **Healthy** — installed, wired, all files present
76
- - **Degraded** — installed but missing wiring or files
77
- - **Not installed** — framework not detected
69
+ - **Healthy** — module files exist + commands installed + hooks/MCP wired (if applicable)
70
+ - **Degraded** — module files exist but missing commands, hooks, or MCP wiring
71
+ - **Not installed** — in manifest but files missing (corrupted install)
78
72
  </step>
79
73
 
80
74
  <step name="report">
81
- Present the status report.
82
-
83
75
  Format:
84
76
  ```
85
- Mission Control Status
77
+ Accelerate Status (v{version})
86
78
 
87
- Framework Version Status Notes
88
- ───────── ─────── ────── ─────
89
- Vector v2.0.0 Healthy hook + MCP wired
90
- Momentum v3.0.1 Degraded hooks not wired (run /momentum:scaffold)
91
- Drive v1.2.0 Healthy 28 commands installed
92
- Ignition v1.0.0 Healthy
93
- Forge v1.0.0 Healthy
94
- Radar v0.2.0 Healthy 10 commands, 3/8 tools installed
79
+ Module Status Notes
80
+ ────── ────── ─────
81
+ Vector Healthy hook + MCP wired
82
+ Momentum Healthy {N} hooks wired, MCP active
83
+ Drive Healthy {N} commands
84
+ Ignition Healthy {N} commands
85
+ Radar Degraded {N} commands, scan tools missing
86
+ Forge Healthy {N} commands
87
+ Mission Ctrl Healthy orchestrator active
95
88
 
96
- Workspace: {workspace name from .accel/momentum/workspace.json}
97
- Drift score: {from .accel/momentum/data/state.json}
98
- Last groom: {date}
89
+ Installed: {date}
90
+ Modules: {count}/7
99
91
 
100
92
  Issues:
101
- - {any degraded items with fix instructions}
102
-
103
- Run /accel install {framework} to install missing frameworks.
104
- Run /accel insights for project-level analytics.
93
+ - Radar: scan tools not installed
94
+ Fix: brew install semgrep trivy gitleaks
95
+
96
+ Quick commands:
97
+ /momentum:scaffold — set up workspace tracking
98
+ /drive:init — initialize dev workflow
99
+ /ignition:ideate — start a new project
100
+ /radar:audit — run security audit
105
101
  ```
106
102
 
107
- If all healthy, end with: "All frameworks healthy."
108
- If issues found, list each with the fix command.
103
+ If all healthy: "All modules healthy."
104
+ If Radar tools missing: suggest brew install.
105
+ If hooks not wired: suggest `npx @accelerationguy/accel@latest` reinstall.
109
106
  </step>
110
107
 
111
108
  </steps>
112
109
 
113
110
  <output>
114
- Status table showing all 7 frameworks with version, health state, and any issues. Actionable fix instructions for any degraded frameworks.
111
+ Status table showing all modules with health state and actionable fix instructions.
115
112
  </output>
116
113
 
117
114
  <acceptance-criteria>
118
- - [ ] All 7 frameworks checked for installation state
119
- - [ ] Versions detected where possible
120
- - [ ] Wiring verified (hooks in settings.json, MCPs in .mcp.json)
121
- - [ ] Health state assigned (Healthy/Degraded/Not installed)
122
- - [ ] Workspace metadata included (name, drift, groom date)
123
- - [ ] Issues listed with fix instructions
124
- - [ ] Output formatted as clean, scannable table
115
+ - [ ] Reads manifest from ~/.accel/manifest.json
116
+ - [ ] All installed modules checked at ~/.accel/modules/{id}/
117
+ - [ ] Commands verified at ~/.claude/commands/{id}/
118
+ - [ ] Hooks verified in ~/.claude/settings.json (Vector, Momentum)
119
+ - [ ] MCP verified in ~/.mcp.json (Vector, Momentum)
120
+ - [ ] Health state assigned per module
121
+ - [ ] Issues listed with fix commands
122
+ - [ ] Clean table format
125
123
  </acceptance-criteria>
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@accelerationguy/accel",
3
- "version": "1.0.1",
3
+ "version": "1.0.3",
4
4
  "description": "Accelerate — Unified Claude Code Agent Framework by Acceleration Guy",
5
5
  "bin": {
6
6
  "accel": "./bin/install.js"