claudenv 1.0.1 → 1.1.0

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.
Files changed (22) hide show
  1. package/README.md +66 -104
  2. package/bin/cli.js +69 -8
  3. package/package.json +8 -8
  4. package/scaffold/.claude/commands/setup-mcp.md +115 -0
  5. package/scaffold/.claude/commands/update-docs.md +1 -0
  6. package/scaffold/.claude/skills/doc-generator/SKILL.md +3 -0
  7. package/scaffold/.claude/skills/doc-generator/templates/mcp-servers.md +168 -0
  8. package/scaffold/global/.claude/commands/claudenv.md +193 -0
  9. package/scaffold/global/.claude/commands/setup-mcp.md +115 -0
  10. package/scaffold/global/.claude/skills/claudenv/SKILL.md +59 -0
  11. package/scaffold/global/.claude/skills/claudenv/scaffold/.claude/agents/doc-analyzer.md +70 -0
  12. package/scaffold/global/.claude/skills/claudenv/scaffold/.claude/commands/init-docs.md +69 -0
  13. package/scaffold/global/.claude/skills/claudenv/scaffold/.claude/commands/setup-mcp.md +115 -0
  14. package/scaffold/global/.claude/skills/claudenv/scaffold/.claude/commands/update-docs.md +50 -0
  15. package/scaffold/global/.claude/skills/claudenv/scaffold/.claude/commands/validate-docs.md +40 -0
  16. package/scaffold/global/.claude/skills/claudenv/scaffold/.claude/skills/doc-generator/SKILL.md +59 -0
  17. package/scaffold/global/.claude/skills/claudenv/scaffold/.claude/skills/doc-generator/scripts/validate.sh +108 -0
  18. package/scaffold/global/.claude/skills/claudenv/scaffold/.claude/skills/doc-generator/templates/detection-patterns.md +76 -0
  19. package/scaffold/global/.claude/skills/claudenv/scaffold/.claude/skills/doc-generator/templates/mcp-servers.md +168 -0
  20. package/scaffold/global/.claude/skills/claudenv/templates/detection-patterns.md +76 -0
  21. package/scaffold/global/.claude/skills/claudenv/templates/mcp-servers.md +168 -0
  22. package/src/installer.js +109 -0
@@ -0,0 +1,109 @@
1
+ import { mkdir, cp, rm, readdir, stat } from 'node:fs/promises';
2
+ import { join, dirname, relative } from 'node:path';
3
+ import { homedir } from 'node:os';
4
+ import { fileURLToPath } from 'node:url';
5
+
6
+ const __dirname = dirname(fileURLToPath(import.meta.url));
7
+ const SCAFFOLD_GLOBAL = join(__dirname, '..', 'scaffold', 'global');
8
+
9
+ /**
10
+ * Get the path to ~/.claude/
11
+ */
12
+ function getClaudeHome() {
13
+ return join(homedir(), '.claude');
14
+ }
15
+
16
+ /**
17
+ * Recursively list all files in a directory (relative paths).
18
+ */
19
+ async function listFiles(dir, base = dir) {
20
+ const entries = await readdir(dir, { withFileTypes: true });
21
+ const files = [];
22
+ for (const entry of entries) {
23
+ const full = join(dir, entry.name);
24
+ if (entry.isDirectory()) {
25
+ files.push(...await listFiles(full, base));
26
+ } else {
27
+ files.push(relative(base, full));
28
+ }
29
+ }
30
+ return files;
31
+ }
32
+
33
+ /**
34
+ * Install global Claude Code artifacts to ~/.claude/.
35
+ * Copies scaffold/global/.claude/ contents into ~/.claude/.
36
+ *
37
+ * @param {object} [options]
38
+ * @param {boolean} [options.force] - Overwrite existing files
39
+ * @param {string} [options.claudeHome] - Override ~/.claude/ path (for testing)
40
+ * @returns {Promise<{written: string[], skipped: string[]}>}
41
+ */
42
+ export async function installGlobal(options = {}) {
43
+ const { force = false, claudeHome } = options;
44
+ const targetBase = claudeHome || getClaudeHome();
45
+ const sourceBase = join(SCAFFOLD_GLOBAL, '.claude');
46
+
47
+ const files = await listFiles(sourceBase);
48
+ const written = [];
49
+ const skipped = [];
50
+
51
+ for (const relPath of files) {
52
+ const src = join(sourceBase, relPath);
53
+ const dest = join(targetBase, relPath);
54
+
55
+ // Check if file exists and skip unless force
56
+ if (!force) {
57
+ try {
58
+ await stat(dest);
59
+ skipped.push(relPath);
60
+ continue;
61
+ } catch {
62
+ // File doesn't exist — proceed
63
+ }
64
+ }
65
+
66
+ await mkdir(dirname(dest), { recursive: true });
67
+ await cp(src, dest);
68
+
69
+ // Make .sh files executable
70
+ if (relPath.endsWith('.sh')) {
71
+ const { chmod } = await import('node:fs/promises');
72
+ await chmod(dest, 0o755);
73
+ }
74
+
75
+ written.push(relPath);
76
+ }
77
+
78
+ return { written, skipped };
79
+ }
80
+
81
+ /**
82
+ * Remove global Claude Code artifacts from ~/.claude/.
83
+ *
84
+ * @param {object} [options]
85
+ * @param {string} [options.claudeHome] - Override ~/.claude/ path (for testing)
86
+ * @returns {Promise<{removed: string[]}>}
87
+ */
88
+ export async function uninstallGlobal(options = {}) {
89
+ const { claudeHome } = options;
90
+ const targetBase = claudeHome || getClaudeHome();
91
+ const removed = [];
92
+
93
+ const targets = [
94
+ join(targetBase, 'commands', 'claudenv.md'),
95
+ join(targetBase, 'skills', 'claudenv'),
96
+ ];
97
+
98
+ for (const target of targets) {
99
+ try {
100
+ await stat(target);
101
+ await rm(target, { recursive: true });
102
+ removed.push(relative(targetBase, target));
103
+ } catch {
104
+ // Doesn't exist — skip
105
+ }
106
+ }
107
+
108
+ return { removed };
109
+ }