@xylabs/ts-scripts-yarn3 7.4.20 → 7.4.22
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/dist/actions/claude-clean.mjs +71 -0
- package/dist/actions/claude-clean.mjs.map +1 -0
- package/dist/actions/claude-commands.mjs +11 -2
- package/dist/actions/claude-commands.mjs.map +1 -1
- package/dist/actions/claude-rules.mjs +27 -7
- package/dist/actions/claude-rules.mjs.map +1 -1
- package/dist/actions/claude-skills.mjs.map +1 -1
- package/dist/actions/dupdeps.mjs +3 -2
- package/dist/actions/dupdeps.mjs.map +1 -1
- package/dist/actions/gitignore.mjs +152 -0
- package/dist/actions/gitignore.mjs.map +1 -0
- package/dist/actions/index.mjs +392 -206
- package/dist/actions/index.mjs.map +1 -1
- package/dist/bin/xy.mjs +432 -226
- package/dist/bin/xy.mjs.map +1 -1
- package/dist/index.d.ts +11 -3
- package/dist/index.mjs +495 -282
- package/dist/index.mjs.map +1 -1
- package/dist/lib/claudeMdTemplate.mjs +5 -1
- package/dist/lib/claudeMdTemplate.mjs.map +1 -1
- package/dist/lib/gitignoreTemplate.mjs +12 -0
- package/dist/lib/gitignoreTemplate.mjs.map +1 -0
- package/dist/lib/index.mjs +17 -3
- package/dist/lib/index.mjs.map +1 -1
- package/dist/xy/build/buildCommand.mjs +161 -0
- package/dist/xy/build/buildCommand.mjs.map +1 -0
- package/dist/xy/build/compileCommand.mjs +174 -0
- package/dist/xy/build/compileCommand.mjs.map +1 -0
- package/dist/xy/build/compileOnlyCommand.mjs +175 -0
- package/dist/xy/build/compileOnlyCommand.mjs.map +1 -0
- package/dist/xy/build/copyAssetsCommand.mjs +84 -0
- package/dist/xy/build/copyAssetsCommand.mjs.map +1 -0
- package/dist/xy/{build-commands → build}/index.mjs +45 -40
- package/dist/xy/build/index.mjs.map +1 -0
- package/dist/xy/build/rebuildCommand.mjs +114 -0
- package/dist/xy/build/rebuildCommand.mjs.map +1 -0
- package/dist/xy/build/recompileCommand.mjs +204 -0
- package/dist/xy/build/recompileCommand.mjs.map +1 -0
- package/dist/xy/common/claude/cleanCommand.mjs +79 -0
- package/dist/xy/common/claude/cleanCommand.mjs.map +1 -0
- package/dist/xy/common/claude/commandsCommand.mjs +11 -2
- package/dist/xy/common/claude/commandsCommand.mjs.map +1 -1
- package/dist/xy/common/claude/index.mjs +171 -69
- package/dist/xy/common/claude/index.mjs.map +1 -1
- package/dist/xy/common/claude/initCommand.mjs +38 -115
- package/dist/xy/common/claude/initCommand.mjs.map +1 -1
- package/dist/xy/common/claude/rulesCommand.mjs +27 -7
- package/dist/xy/common/claude/rulesCommand.mjs.map +1 -1
- package/dist/xy/common/claude/skillsCommand.mjs.map +1 -1
- package/dist/xy/common/gitignoreCommand.mjs +158 -0
- package/dist/xy/common/gitignoreCommand.mjs.map +1 -0
- package/dist/xy/common/index.mjs +304 -109
- package/dist/xy/common/index.mjs.map +1 -1
- package/dist/xy/index.mjs +432 -226
- package/dist/xy/index.mjs.map +1 -1
- package/dist/xy/install/dupdepsCommand.mjs +3 -2
- package/dist/xy/install/dupdepsCommand.mjs.map +1 -1
- package/dist/xy/install/index.mjs +3 -2
- package/dist/xy/install/index.mjs.map +1 -1
- package/dist/xy/xy.mjs +432 -226
- package/dist/xy/xy.mjs.map +1 -1
- package/package.json +2 -2
- package/templates/claude/CLAUDE-local.md +4 -0
- package/templates/claude/commands/xy-dead.md +5 -0
- package/templates/claude/{rules/xylabs-dependencies.md → commands/xy-deps.md} +7 -7
- package/templates/claude/commands/xy-dupdeps.md +5 -0
- package/templates/claude/commands/xy-gen-docs.md +5 -0
- package/templates/claude/commands/xy-gitignore.md +5 -0
- package/templates/claude/commands/xy-gitlint.md +5 -0
- package/templates/claude/commands/xy-license.md +5 -0
- package/templates/claude/commands/xy-lint-rules.md +44 -0
- package/templates/claude/commands/xy-recompile.md +5 -0
- package/templates/claude/commands/xy-reinstall.md +5 -0
- package/templates/claude/commands/xy-relint.md +5 -0
- package/templates/claude/commands/xy-retest.md +5 -0
- package/templates/claude/commands/xy-sonar.md +5 -0
- package/templates/claude/commands/xy-up.md +7 -0
- package/templates/claude/rules/xylabs-architecture.md +4 -7
- package/templates/claude/rules/xylabs-build.md +6 -11
- package/templates/claude/rules/xylabs-git-workflow.md +3 -5
- package/templates/claude/rules/xylabs-naming.md +4 -7
- package/templates/claude/rules/xylabs-style.md +14 -19
- package/templates/claude/skills/xylabs-e2e-setup/SKILL.md +16 -2
- package/templates/gitignore/template.gitignore +40 -0
- package/dist/actions/gitignore-gen.mjs +0 -88
- package/dist/actions/gitignore-gen.mjs.map +0 -1
- package/dist/xy/build-commands/build.mjs +0 -502
- package/dist/xy/build-commands/build.mjs.map +0 -1
- package/dist/xy/build-commands/index.mjs.map +0 -1
- package/dist/xy/common/gitignoreGenCommand.mjs +0 -98
- package/dist/xy/common/gitignoreGenCommand.mjs.map +0 -1
- package/templates/claude/commands/xylabs-deploy-major.md +0 -7
- package/templates/claude/commands/xylabs-deploy-minor.md +0 -7
- package/templates/claude/commands/xylabs-deploy.md +0 -7
- package/templates/claude/rules/xylabs-error-handling.md +0 -7
- package/templates/claude/rules/xylabs-frameworks.md +0 -8
- package/templates/claude/rules/xylabs-linting.md +0 -55
- package/templates/claude/rules/xylabs-typescript.md +0 -11
- /package/templates/claude/commands/{xylabs-build.md → xy-build.md} +0 -0
- /package/templates/claude/commands/{xylabs-clean.md → xy-clean.md} +0 -0
- /package/templates/claude/commands/{xylabs-compile.md → xy-compile.md} +0 -0
- /package/templates/claude/commands/{xylabs-cycle.md → xy-cycle.md} +0 -0
- /package/templates/claude/commands/{xylabs-deplint.md → xy-deplint.md} +0 -0
- /package/templates/claude/commands/{xylabs-fix.md → xy-fix.md} +0 -0
- /package/templates/claude/commands/{xylabs-knip.md → xy-knip.md} +0 -0
- /package/templates/claude/commands/{xylabs-lint.md → xy-lint.md} +0 -0
- /package/templates/claude/commands/{xylabs-publint.md → xy-publint.md} +0 -0
- /package/templates/claude/commands/{xylabs-rebuild.md → xy-rebuild.md} +0 -0
- /package/templates/claude/commands/{xylabs-test.md → xy-test.md} +0 -0
|
@@ -10,8 +10,8 @@ var require2 = createRequire(import.meta.url);
|
|
|
10
10
|
var packageRoot = PATH.dirname(require2.resolve("@xylabs/ts-scripts-yarn3/package.json"));
|
|
11
11
|
var templatesDir = PATH.resolve(packageRoot, "templates", "claude");
|
|
12
12
|
var XYLABS_RULES_PREFIX = "xylabs-";
|
|
13
|
-
var XYLABS_COMMANDS_PREFIX = "
|
|
14
|
-
var
|
|
13
|
+
var XYLABS_COMMANDS_PREFIX = "xy-";
|
|
14
|
+
var LEGACY_COMMANDS_PREFIX = "xylabs-";
|
|
15
15
|
var claudeMdRuleTemplates = () => {
|
|
16
16
|
const rulesDir = PATH.resolve(templatesDir, "rules");
|
|
17
17
|
const files = readdirSync(rulesDir).filter((f) => f.startsWith(XYLABS_RULES_PREFIX) && f.endsWith(".md"));
|
|
@@ -30,25 +30,7 @@ var claudeCommandTemplates = () => {
|
|
|
30
30
|
}
|
|
31
31
|
return result;
|
|
32
32
|
};
|
|
33
|
-
var
|
|
34
|
-
const skillsDir = PATH.resolve(templatesDir, "skills");
|
|
35
|
-
const dirs = readdirSync(skillsDir).filter(
|
|
36
|
-
(f) => f.startsWith(XYLABS_SKILLS_PREFIX) && statSync(PATH.resolve(skillsDir, f)).isDirectory()
|
|
37
|
-
);
|
|
38
|
-
const result = {};
|
|
39
|
-
for (const dir of dirs) {
|
|
40
|
-
const dirPath = PATH.resolve(skillsDir, dir);
|
|
41
|
-
const files = readdirSync(dirPath, { recursive: true, encoding: "utf8" });
|
|
42
|
-
result[dir] = {};
|
|
43
|
-
for (const file of files) {
|
|
44
|
-
if (statSync(PATH.resolve(dirPath, file)).isFile()) {
|
|
45
|
-
result[dir][file] = readFileSync(PATH.resolve(dirPath, file), "utf8");
|
|
46
|
-
}
|
|
47
|
-
}
|
|
48
|
-
}
|
|
49
|
-
return result;
|
|
50
|
-
};
|
|
51
|
-
var claudeMdProjectTemplate = () => readFileSync(PATH.resolve(templatesDir, "CLAUDE-project.md"), "utf8");
|
|
33
|
+
var claudeMdLocalTemplate = () => readFileSync(PATH.resolve(templatesDir, "CLAUDE-local.md"), "utf8");
|
|
52
34
|
|
|
53
35
|
// src/lib/yarn/yarnInitCwd.ts
|
|
54
36
|
var INIT_CWD = () => {
|
|
@@ -100,6 +82,13 @@ var removeStaleCommands = (commandsDir, templateNames) => {
|
|
|
100
82
|
}
|
|
101
83
|
return removed;
|
|
102
84
|
};
|
|
85
|
+
var removeLegacyCommands = (commandsDir) => {
|
|
86
|
+
const legacyFiles = readdirSync2(commandsDir).filter((f) => f.startsWith(LEGACY_COMMANDS_PREFIX) && f.endsWith(".md"));
|
|
87
|
+
for (const file of legacyFiles) {
|
|
88
|
+
unlinkSync(PATH2.resolve(commandsDir, file));
|
|
89
|
+
}
|
|
90
|
+
return legacyFiles.length;
|
|
91
|
+
};
|
|
103
92
|
var logCommandsResult = (created, updated, removed) => {
|
|
104
93
|
if (created || updated || removed) {
|
|
105
94
|
const parts = [
|
|
@@ -116,17 +105,19 @@ var claudeCommands = () => {
|
|
|
116
105
|
const cwd = INIT_CWD() ?? process.cwd();
|
|
117
106
|
const commandsDir = PATH2.resolve(cwd, ".claude", "commands");
|
|
118
107
|
mkdirSync(commandsDir, { recursive: true });
|
|
108
|
+
const legacy = removeLegacyCommands(commandsDir);
|
|
119
109
|
const {
|
|
120
110
|
created,
|
|
121
111
|
templateNames,
|
|
122
112
|
updated
|
|
123
113
|
} = syncCommandFiles(commandsDir);
|
|
124
114
|
const removed = removeStaleCommands(commandsDir, templateNames);
|
|
125
|
-
logCommandsResult(created, updated, removed);
|
|
115
|
+
logCommandsResult(created, updated, removed + legacy);
|
|
126
116
|
return 0;
|
|
127
117
|
};
|
|
128
118
|
|
|
129
119
|
// src/actions/claude-rules.ts
|
|
120
|
+
import { spawnSync } from "child_process";
|
|
130
121
|
import {
|
|
131
122
|
existsSync as existsSync2,
|
|
132
123
|
mkdirSync as mkdirSync2,
|
|
@@ -186,12 +177,30 @@ var ensureProjectClaudeMd = (cwd, force) => {
|
|
|
186
177
|
const projectPath = PATH3.resolve(cwd, "CLAUDE.md");
|
|
187
178
|
if (!existsSync2(projectPath) || force) {
|
|
188
179
|
if (force && existsSync2(projectPath)) {
|
|
189
|
-
console.log(chalk2.yellow("
|
|
180
|
+
console.log(chalk2.yellow("Regenerating CLAUDE.md"));
|
|
190
181
|
}
|
|
191
|
-
|
|
192
|
-
|
|
182
|
+
console.log(chalk2.green("Generating CLAUDE.md via claude /init..."));
|
|
183
|
+
const result = spawnSync("claude", ["-p", "/init", "--allowedTools", "Read", "Write", "Glob", "Grep"], {
|
|
184
|
+
cwd,
|
|
185
|
+
shell: true,
|
|
186
|
+
stdio: "inherit"
|
|
187
|
+
});
|
|
188
|
+
if (result.status !== 0) {
|
|
189
|
+
console.error(chalk2.red("claude /init failed \u2014 is Claude Code installed?"));
|
|
190
|
+
return 1;
|
|
191
|
+
}
|
|
192
|
+
} else {
|
|
193
|
+
console.log(chalk2.gray("CLAUDE.md already exists (skipped, use --force to regenerate)"));
|
|
194
|
+
}
|
|
195
|
+
return 0;
|
|
196
|
+
};
|
|
197
|
+
var ensureLocalClaudeMd = (cwd) => {
|
|
198
|
+
const localPath = PATH3.resolve(cwd, "CLAUDE.local.md");
|
|
199
|
+
if (existsSync2(localPath)) {
|
|
200
|
+
console.log(chalk2.gray("CLAUDE.local.md already exists (skipped)"));
|
|
193
201
|
} else {
|
|
194
|
-
|
|
202
|
+
writeFileSync2(localPath, claudeMdLocalTemplate(), "utf8");
|
|
203
|
+
console.log(chalk2.green("Generated CLAUDE.local.md"));
|
|
195
204
|
}
|
|
196
205
|
};
|
|
197
206
|
var claudeRules = ({ force } = {}) => {
|
|
@@ -205,8 +214,9 @@ var claudeRules = ({ force } = {}) => {
|
|
|
205
214
|
} = syncRuleFiles(rulesDir);
|
|
206
215
|
const removed = removeStaleRules(rulesDir, templateNames);
|
|
207
216
|
logRulesResult(created, updated, removed);
|
|
208
|
-
ensureProjectClaudeMd(cwd, force);
|
|
209
|
-
|
|
217
|
+
const claudeMdResult = ensureProjectClaudeMd(cwd, force);
|
|
218
|
+
ensureLocalClaudeMd(cwd);
|
|
219
|
+
return claudeMdResult ?? 0;
|
|
210
220
|
};
|
|
211
221
|
|
|
212
222
|
// src/actions/claude-settings.ts
|
|
@@ -280,84 +290,6 @@ async function claudeSettings() {
|
|
|
280
290
|
return 0;
|
|
281
291
|
}
|
|
282
292
|
|
|
283
|
-
// src/actions/claude-skills.ts
|
|
284
|
-
import {
|
|
285
|
-
existsSync as existsSync4,
|
|
286
|
-
mkdirSync as mkdirSync4,
|
|
287
|
-
readdirSync as readdirSync4,
|
|
288
|
-
readFileSync as readFileSync4,
|
|
289
|
-
rmSync,
|
|
290
|
-
statSync as statSync2,
|
|
291
|
-
writeFileSync as writeFileSync4
|
|
292
|
-
} from "fs";
|
|
293
|
-
import PATH5 from "path";
|
|
294
|
-
import chalk4 from "chalk";
|
|
295
|
-
var syncSkillFiles = (skillsDir) => {
|
|
296
|
-
const templates = claudeSkillTemplates();
|
|
297
|
-
const templateNames = new Set(Object.keys(templates));
|
|
298
|
-
let updated = 0;
|
|
299
|
-
let created = 0;
|
|
300
|
-
for (const [skillName, files] of Object.entries(templates)) {
|
|
301
|
-
const skillDir = PATH5.resolve(skillsDir, skillName);
|
|
302
|
-
mkdirSync4(skillDir, { recursive: true });
|
|
303
|
-
for (const [filename, content] of Object.entries(files)) {
|
|
304
|
-
const targetPath = PATH5.resolve(skillDir, filename);
|
|
305
|
-
mkdirSync4(PATH5.dirname(targetPath), { recursive: true });
|
|
306
|
-
const existing = existsSync4(targetPath) ? readFileSync4(targetPath, "utf8") : void 0;
|
|
307
|
-
if (existing === content) continue;
|
|
308
|
-
writeFileSync4(targetPath, content, "utf8");
|
|
309
|
-
if (existing) {
|
|
310
|
-
updated++;
|
|
311
|
-
} else {
|
|
312
|
-
created++;
|
|
313
|
-
}
|
|
314
|
-
}
|
|
315
|
-
}
|
|
316
|
-
return {
|
|
317
|
-
created,
|
|
318
|
-
templateNames,
|
|
319
|
-
updated
|
|
320
|
-
};
|
|
321
|
-
};
|
|
322
|
-
var removeStaleSkills = (skillsDir, templateNames) => {
|
|
323
|
-
const existingSkills = readdirSync4(skillsDir).filter(
|
|
324
|
-
(f) => f.startsWith(XYLABS_SKILLS_PREFIX) && statSync2(PATH5.resolve(skillsDir, f)).isDirectory()
|
|
325
|
-
);
|
|
326
|
-
let removed = 0;
|
|
327
|
-
for (const dir of existingSkills) {
|
|
328
|
-
if (!templateNames.has(dir)) {
|
|
329
|
-
rmSync(PATH5.resolve(skillsDir, dir), { recursive: true });
|
|
330
|
-
removed++;
|
|
331
|
-
}
|
|
332
|
-
}
|
|
333
|
-
return removed;
|
|
334
|
-
};
|
|
335
|
-
var logSkillsResult = (created, updated, removed) => {
|
|
336
|
-
if (created || updated || removed) {
|
|
337
|
-
const parts = [
|
|
338
|
-
created ? `${created} created` : "",
|
|
339
|
-
updated ? `${updated} updated` : "",
|
|
340
|
-
removed ? `${removed} removed` : ""
|
|
341
|
-
].filter(Boolean);
|
|
342
|
-
console.log(chalk4.green(`.claude/skills/${XYLABS_SKILLS_PREFIX}*/: ${parts.join(", ")}`));
|
|
343
|
-
} else {
|
|
344
|
-
console.log(chalk4.gray(`.claude/skills/${XYLABS_SKILLS_PREFIX}*/: already up to date`));
|
|
345
|
-
}
|
|
346
|
-
};
|
|
347
|
-
var claudeSkills = () => {
|
|
348
|
-
const cwd = INIT_CWD() ?? process.cwd();
|
|
349
|
-
const skillsDir = PATH5.resolve(cwd, ".claude", "skills");
|
|
350
|
-
mkdirSync4(skillsDir, { recursive: true });
|
|
351
|
-
const {
|
|
352
|
-
created,
|
|
353
|
-
templateNames,
|
|
354
|
-
updated
|
|
355
|
-
} = syncSkillFiles(skillsDir);
|
|
356
|
-
const removed = removeStaleSkills(skillsDir, templateNames);
|
|
357
|
-
logSkillsResult(created, updated, removed);
|
|
358
|
-
return 0;
|
|
359
|
-
};
|
|
360
|
-
|
|
361
293
|
// src/xy/common/claude/initCommand.ts
|
|
362
294
|
var initCommand = {
|
|
363
295
|
builder: (yargs) => {
|
|
@@ -378,16 +310,7 @@ var initCommand = {
|
|
|
378
310
|
process.exitCode = commandsResult || rulesResult || settingsResult;
|
|
379
311
|
}
|
|
380
312
|
};
|
|
381
|
-
var initClaudeSkillsCommand = {
|
|
382
|
-
command: "init:skills",
|
|
383
|
-
describe: "Initialize Claude skills configuration",
|
|
384
|
-
handler: () => {
|
|
385
|
-
const result = claudeSkills();
|
|
386
|
-
process.exitCode = result;
|
|
387
|
-
}
|
|
388
|
-
};
|
|
389
313
|
export {
|
|
390
|
-
initClaudeSkillsCommand,
|
|
391
314
|
initCommand
|
|
392
315
|
};
|
|
393
316
|
//# sourceMappingURL=initCommand.mjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../../src/lib/claudeMdTemplate.ts","../../../../src/lib/yarn/yarnInitCwd.ts","../../../../src/actions/claude-commands.ts","../../../../src/actions/claude-rules.ts","../../../../src/actions/claude-settings.ts","../../../../src/actions/claude-skills.ts","../../../../src/xy/common/claude/initCommand.ts"],"sourcesContent":["import {\n readdirSync, readFileSync, statSync,\n} from 'node:fs'\nimport { createRequire } from 'node:module'\nimport PATH from 'node:path'\n\nconst require = createRequire(import.meta.url)\nconst packageRoot = PATH.dirname(require.resolve('@xylabs/ts-scripts-yarn3/package.json'))\nconst templatesDir = PATH.resolve(packageRoot, 'templates', 'claude')\n\nexport const XYLABS_RULES_PREFIX = 'xylabs-'\nexport const XYLABS_COMMANDS_PREFIX = 'xylabs-'\nexport const XYLABS_SKILLS_PREFIX = 'xylabs-'\n\nexport const claudeMdRuleTemplates = (): Record<string, string> => {\n const rulesDir = PATH.resolve(templatesDir, 'rules')\n const files = readdirSync(rulesDir).filter(f => f.startsWith(XYLABS_RULES_PREFIX) && f.endsWith('.md'))\n const result: Record<string, string> = {}\n for (const file of files) {\n result[file] = readFileSync(PATH.resolve(rulesDir, file), 'utf8')\n }\n return result\n}\n\nexport const claudeCommandTemplates = (): Record<string, string> => {\n const commandsDir = PATH.resolve(templatesDir, 'commands')\n const files = readdirSync(commandsDir).filter(f => f.startsWith(XYLABS_COMMANDS_PREFIX) && f.endsWith('.md'))\n const result: Record<string, string> = {}\n for (const file of files) {\n result[file] = readFileSync(PATH.resolve(commandsDir, file), 'utf8')\n }\n return result\n}\n\n// Returns { 'xylabs-foo': { 'SKILL.md': '...', 'other.ts': '...' } }\nexport const claudeSkillTemplates = (): Record<string, Record<string, string>> => {\n const skillsDir = PATH.resolve(templatesDir, 'skills')\n const dirs = readdirSync(skillsDir).filter(\n f => f.startsWith(XYLABS_SKILLS_PREFIX) && statSync(PATH.resolve(skillsDir, f)).isDirectory(),\n )\n const result: Record<string, Record<string, string>> = {}\n for (const dir of dirs) {\n const dirPath = PATH.resolve(skillsDir, dir)\n const files = readdirSync(dirPath, { recursive: true, encoding: 'utf8' }) as string[]\n result[dir] = {}\n for (const file of files) {\n if (statSync(PATH.resolve(dirPath, file)).isFile()) {\n result[dir][file] = readFileSync(PATH.resolve(dirPath, file), 'utf8')\n }\n }\n }\n return result\n}\n\nexport const claudeMdProjectTemplate = (): string =>\n readFileSync(PATH.resolve(templatesDir, 'CLAUDE-project.md'), 'utf8')\n","export const INIT_CWD = () => {\n if (!process.env.INIT_CWD) console.error('Missing INIT_CWD')\n return process.env.INIT_CWD\n}\n","import {\n existsSync, mkdirSync, readdirSync, readFileSync, unlinkSync, writeFileSync,\n} from 'node:fs'\nimport PATH from 'node:path'\n\nimport chalk from 'chalk'\n\nimport { claudeCommandTemplates, XYLABS_COMMANDS_PREFIX } from '../lib/index.ts'\nimport { INIT_CWD } from '../lib/yarn/index.ts'\n\nconst syncCommandFiles = (commandsDir: string) => {\n const templates = claudeCommandTemplates()\n const templateNames = new Set(Object.keys(templates))\n let updated = 0\n let created = 0\n\n for (const [filename, content] of Object.entries(templates)) {\n const targetPath = PATH.resolve(commandsDir, filename)\n const existing = existsSync(targetPath) ? readFileSync(targetPath, 'utf8') : undefined\n if (existing === content) continue\n writeFileSync(targetPath, content, 'utf8')\n if (existing) {\n updated++\n } else {\n created++\n }\n }\n\n return {\n created, templateNames, updated,\n }\n}\n\nconst removeStaleCommands = (commandsDir: string, templateNames: Set<string>) => {\n const existingCommands = readdirSync(commandsDir).filter(f => f.startsWith(XYLABS_COMMANDS_PREFIX) && f.endsWith('.md'))\n let removed = 0\n\n for (const file of existingCommands) {\n if (!templateNames.has(file)) {\n unlinkSync(PATH.resolve(commandsDir, file))\n removed++\n }\n }\n\n return removed\n}\n\nconst logCommandsResult = (created: number, updated: number, removed: number) => {\n if (created || updated || removed) {\n const parts = [\n created ? `${created} created` : '',\n updated ? `${updated} updated` : '',\n removed ? `${removed} removed` : '',\n ].filter(Boolean)\n console.log(chalk.green(`.claude/commands/${XYLABS_COMMANDS_PREFIX}*.md: ${parts.join(', ')}`))\n } else {\n console.log(chalk.gray(`.claude/commands/${XYLABS_COMMANDS_PREFIX}*.md: already up to date`))\n }\n}\n\nexport const claudeCommands = (): number => {\n const cwd = INIT_CWD() ?? process.cwd()\n const commandsDir = PATH.resolve(cwd, '.claude', 'commands')\n\n mkdirSync(commandsDir, { recursive: true })\n\n const {\n created, templateNames, updated,\n } = syncCommandFiles(commandsDir)\n const removed = removeStaleCommands(commandsDir, templateNames)\n logCommandsResult(created, updated, removed)\n\n return 0\n}\n","import {\n existsSync, mkdirSync, readdirSync, readFileSync, unlinkSync, writeFileSync,\n} from 'node:fs'\nimport PATH from 'node:path'\n\nimport chalk from 'chalk'\n\nimport {\n claudeMdProjectTemplate, claudeMdRuleTemplates, XYLABS_RULES_PREFIX,\n} from '../lib/index.ts'\nimport { INIT_CWD } from '../lib/yarn/index.ts'\n\nconst syncRuleFiles = (rulesDir: string) => {\n const templates = claudeMdRuleTemplates()\n const templateNames = new Set(Object.keys(templates))\n let updated = 0\n let created = 0\n\n for (const [filename, content] of Object.entries(templates)) {\n const targetPath = PATH.resolve(rulesDir, filename)\n const existing = existsSync(targetPath) ? readFileSync(targetPath, 'utf8') : undefined\n if (existing === content) continue\n writeFileSync(targetPath, content, 'utf8')\n if (existing) {\n updated++\n } else {\n created++\n }\n }\n\n return {\n created, templateNames, updated,\n }\n}\n\nconst removeStaleRules = (rulesDir: string, templateNames: Set<string>) => {\n const existingRules = readdirSync(rulesDir).filter(f => f.startsWith(XYLABS_RULES_PREFIX) && f.endsWith('.md'))\n let removed = 0\n\n for (const file of existingRules) {\n if (!templateNames.has(file)) {\n unlinkSync(PATH.resolve(rulesDir, file))\n removed++\n }\n }\n\n return removed\n}\n\nconst logRulesResult = (created: number, updated: number, removed: number) => {\n if (created || updated || removed) {\n const parts = [\n created ? `${created} created` : '',\n updated ? `${updated} updated` : '',\n removed ? `${removed} removed` : '',\n ].filter(Boolean)\n console.log(chalk.green(`.claude/rules/${XYLABS_RULES_PREFIX}*.md: ${parts.join(', ')}`))\n } else {\n console.log(chalk.gray(`.claude/rules/${XYLABS_RULES_PREFIX}*.md: already up to date`))\n }\n}\n\nconst ensureProjectClaudeMd = (cwd: string, force?: boolean) => {\n const projectPath = PATH.resolve(cwd, 'CLAUDE.md')\n\n if (!existsSync(projectPath) || force) {\n if (force && existsSync(projectPath)) {\n console.log(chalk.yellow('Overwriting existing CLAUDE.md'))\n }\n writeFileSync(projectPath, claudeMdProjectTemplate(), 'utf8')\n console.log(chalk.green('Generated CLAUDE.md'))\n } else {\n console.log(chalk.gray('CLAUDE.md already exists (skipped)'))\n }\n}\n\nexport const claudeRules = ({ force }: { force?: boolean } = {}): number => {\n const cwd = INIT_CWD() ?? process.cwd()\n const rulesDir = PATH.resolve(cwd, '.claude', 'rules')\n\n mkdirSync(rulesDir, { recursive: true })\n\n const {\n created, templateNames, updated,\n } = syncRuleFiles(rulesDir)\n const removed = removeStaleRules(rulesDir, templateNames)\n logRulesResult(created, updated, removed)\n ensureProjectClaudeMd(cwd, force)\n\n return 0\n}\n","import {\n existsSync, mkdirSync, writeFileSync,\n} from 'node:fs'\nimport PATH from 'node:path'\nimport { createInterface } from 'node:readline'\n\nimport chalk from 'chalk'\n\nimport { INIT_CWD } from '../lib/yarn/index.ts'\n\nconst DEFAULT_SETTINGS = {\n permissions: {\n allow: [\n 'Bash(git *)',\n 'Bash(yarn *)',\n 'Bash(npx *)',\n 'Bash(node *)',\n 'Bash(ls *)',\n 'Bash(mkdir *)',\n 'Bash(cp *)',\n 'Bash(mv *)',\n 'Bash(rm *)',\n 'Bash(cat *)',\n 'Bash(head *)',\n 'Bash(tail *)',\n 'Bash(echo *)',\n 'Bash(pwd)',\n 'Bash(which *)',\n 'Bash(gh *)',\n 'Read',\n 'Edit',\n 'Write',\n 'Glob',\n 'Grep',\n 'Skill',\n ],\n deny: [\n 'Bash(git push --force*)',\n 'Bash(git reset --hard*)',\n 'Bash(rm -rf /*)',\n ],\n },\n}\n\nfunction askConfirmation(question: string): Promise<boolean> {\n const rl = createInterface({ input: process.stdin, output: process.stdout })\n return new Promise((resolve) => {\n rl.question(question, (answer) => {\n rl.close()\n resolve(answer.toLowerCase() === 'y' || answer.toLowerCase() === 'yes')\n })\n })\n}\n\nexport async function claudeSettings(): Promise<number> {\n const cwd = INIT_CWD() ?? process.cwd()\n const claudeDir = PATH.resolve(cwd, '.claude')\n const settingsPath = PATH.resolve(claudeDir, 'settings.local.json')\n\n mkdirSync(claudeDir, { recursive: true })\n\n if (existsSync(settingsPath)) {\n const confirmed = await askConfirmation(\n chalk.yellow(`${settingsPath} already exists. Replace it? (y/N) `),\n )\n if (!confirmed) {\n console.log(chalk.gray('Skipped — existing settings.local.json preserved'))\n return 0\n }\n }\n\n writeFileSync(settingsPath, `${JSON.stringify(DEFAULT_SETTINGS, null, 2)}\\n`, 'utf8')\n console.log(chalk.green('Generated .claude/settings.local.json'))\n return 0\n}\n","import {\n existsSync, mkdirSync, readdirSync, readFileSync, rmSync, statSync, writeFileSync,\n} from 'node:fs'\nimport PATH from 'node:path'\n\nimport chalk from 'chalk'\n\nimport { claudeSkillTemplates, XYLABS_SKILLS_PREFIX } from '../lib/index.ts'\nimport { INIT_CWD } from '../lib/yarn/index.ts'\n\nconst syncSkillFiles = (skillsDir: string) => {\n const templates = claudeSkillTemplates()\n const templateNames = new Set(Object.keys(templates))\n let updated = 0\n let created = 0\n\n for (const [skillName, files] of Object.entries(templates)) {\n const skillDir = PATH.resolve(skillsDir, skillName)\n mkdirSync(skillDir, { recursive: true })\n\n for (const [filename, content] of Object.entries(files)) {\n const targetPath = PATH.resolve(skillDir, filename)\n mkdirSync(PATH.dirname(targetPath), { recursive: true })\n const existing = existsSync(targetPath) ? readFileSync(targetPath, 'utf8') : undefined\n if (existing === content) continue\n writeFileSync(targetPath, content, 'utf8')\n if (existing) {\n updated++\n } else {\n created++\n }\n }\n }\n\n return {\n created, templateNames, updated,\n }\n}\n\nconst removeStaleSkills = (skillsDir: string, templateNames: Set<string>) => {\n const existingSkills = readdirSync(skillsDir).filter(\n f => f.startsWith(XYLABS_SKILLS_PREFIX) && statSync(PATH.resolve(skillsDir, f)).isDirectory(),\n )\n let removed = 0\n\n for (const dir of existingSkills) {\n if (!templateNames.has(dir)) {\n rmSync(PATH.resolve(skillsDir, dir), { recursive: true })\n removed++\n }\n }\n\n return removed\n}\n\nconst logSkillsResult = (created: number, updated: number, removed: number) => {\n if (created || updated || removed) {\n const parts = [\n created ? `${created} created` : '',\n updated ? `${updated} updated` : '',\n removed ? `${removed} removed` : '',\n ].filter(Boolean)\n console.log(chalk.green(`.claude/skills/${XYLABS_SKILLS_PREFIX}*/: ${parts.join(', ')}`))\n } else {\n console.log(chalk.gray(`.claude/skills/${XYLABS_SKILLS_PREFIX}*/: already up to date`))\n }\n}\n\nexport const claudeSkills = (): number => {\n const cwd = INIT_CWD() ?? process.cwd()\n const skillsDir = PATH.resolve(cwd, '.claude', 'skills')\n\n mkdirSync(skillsDir, { recursive: true })\n\n const {\n created, templateNames, updated,\n } = syncSkillFiles(skillsDir)\n const removed = removeStaleSkills(skillsDir, templateNames)\n logSkillsResult(created, updated, removed)\n\n return 0\n}\n","import type { CommandModule } from 'yargs'\n\nimport {\n claudeCommands, claudeRules, claudeSettings, claudeSkills,\n} from '../../../actions/index.ts'\n\nexport const initCommand: CommandModule = {\n builder: (yargs) => {\n return yargs\n .option('force', {\n alias: 'f',\n default: false,\n description: 'Overwrite existing CLAUDE.md',\n type: 'boolean',\n })\n },\n command: 'init',\n describe: 'Initialize all Claude configuration (commands, rules, settings)',\n handler: async (argv) => {\n if (argv.verbose) console.log('Claude Init')\n const commandsResult = claudeCommands()\n const rulesResult = claudeRules({ force: argv.force as boolean | undefined })\n const settingsResult = await claudeSettings()\n process.exitCode = commandsResult || rulesResult || settingsResult\n },\n}\n\nexport const initClaudeSkillsCommand: CommandModule = {\n command: 'init:skills',\n describe: 'Initialize Claude skills configuration',\n handler: () => {\n const result = claudeSkills()\n process.exitCode = result\n },\n}\n"],"mappings":"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","names":["require","readdirSync","readFileSync","PATH","PATH","readFileSync","readdirSync","existsSync","mkdirSync","readdirSync","readFileSync","unlinkSync","writeFileSync","PATH","chalk","PATH","existsSync","readFileSync","writeFileSync","readdirSync","unlinkSync","chalk","mkdirSync","existsSync","mkdirSync","writeFileSync","PATH","chalk","PATH","mkdirSync","existsSync","chalk","writeFileSync","existsSync","mkdirSync","readdirSync","readFileSync","statSync","writeFileSync","PATH","chalk","PATH","mkdirSync","existsSync","readFileSync","writeFileSync","readdirSync","statSync","chalk"]}
|
|
1
|
+
{"version":3,"sources":["../../../../src/lib/claudeMdTemplate.ts","../../../../src/lib/yarn/yarnInitCwd.ts","../../../../src/actions/claude-commands.ts","../../../../src/actions/claude-rules.ts","../../../../src/actions/claude-settings.ts","../../../../src/xy/common/claude/initCommand.ts"],"sourcesContent":["import {\n readdirSync, readFileSync, statSync,\n} from 'node:fs'\nimport { createRequire } from 'node:module'\nimport PATH from 'node:path'\n\nconst require = createRequire(import.meta.url)\nconst packageRoot = PATH.dirname(require.resolve('@xylabs/ts-scripts-yarn3/package.json'))\nconst templatesDir = PATH.resolve(packageRoot, 'templates', 'claude')\n\nexport const XYLABS_RULES_PREFIX = 'xylabs-'\nexport const XYLABS_COMMANDS_PREFIX = 'xy-'\nexport const LEGACY_COMMANDS_PREFIX = 'xylabs-'\nexport const XYLABS_SKILLS_PREFIX = 'xylabs-'\n\nexport const claudeMdRuleTemplates = (): Record<string, string> => {\n const rulesDir = PATH.resolve(templatesDir, 'rules')\n const files = readdirSync(rulesDir).filter(f => f.startsWith(XYLABS_RULES_PREFIX) && f.endsWith('.md'))\n const result: Record<string, string> = {}\n for (const file of files) {\n result[file] = readFileSync(PATH.resolve(rulesDir, file), 'utf8')\n }\n return result\n}\n\nexport const claudeCommandTemplates = (): Record<string, string> => {\n const commandsDir = PATH.resolve(templatesDir, 'commands')\n const files = readdirSync(commandsDir).filter(f => f.startsWith(XYLABS_COMMANDS_PREFIX) && f.endsWith('.md'))\n const result: Record<string, string> = {}\n for (const file of files) {\n result[file] = readFileSync(PATH.resolve(commandsDir, file), 'utf8')\n }\n return result\n}\n\n// Returns { 'xylabs-foo': { 'SKILL.md': '...', 'other.ts': '...' } }\nexport const claudeSkillTemplates = (): Record<string, Record<string, string>> => {\n const skillsDir = PATH.resolve(templatesDir, 'skills')\n const dirs = readdirSync(skillsDir).filter(\n f => f.startsWith(XYLABS_SKILLS_PREFIX) && statSync(PATH.resolve(skillsDir, f)).isDirectory(),\n )\n const result: Record<string, Record<string, string>> = {}\n for (const dir of dirs) {\n const dirPath = PATH.resolve(skillsDir, dir)\n const files = readdirSync(dirPath, { recursive: true, encoding: 'utf8' }) as string[]\n result[dir] = {}\n for (const file of files) {\n if (statSync(PATH.resolve(dirPath, file)).isFile()) {\n result[dir][file] = readFileSync(PATH.resolve(dirPath, file), 'utf8')\n }\n }\n }\n return result\n}\n\nexport const claudeMdProjectTemplate = (): string =>\n readFileSync(PATH.resolve(templatesDir, 'CLAUDE-project.md'), 'utf8')\n\nexport const claudeMdLocalTemplate = (): string =>\n readFileSync(PATH.resolve(templatesDir, 'CLAUDE-local.md'), 'utf8')\n","export const INIT_CWD = () => {\n if (!process.env.INIT_CWD) console.error('Missing INIT_CWD')\n return process.env.INIT_CWD\n}\n","import {\n existsSync, mkdirSync, readdirSync, readFileSync, unlinkSync, writeFileSync,\n} from 'node:fs'\nimport PATH from 'node:path'\n\nimport chalk from 'chalk'\n\nimport {\n claudeCommandTemplates, LEGACY_COMMANDS_PREFIX, XYLABS_COMMANDS_PREFIX,\n} from '../lib/index.ts'\nimport { INIT_CWD } from '../lib/yarn/index.ts'\n\nconst syncCommandFiles = (commandsDir: string) => {\n const templates = claudeCommandTemplates()\n const templateNames = new Set(Object.keys(templates))\n let updated = 0\n let created = 0\n\n for (const [filename, content] of Object.entries(templates)) {\n const targetPath = PATH.resolve(commandsDir, filename)\n const existing = existsSync(targetPath) ? readFileSync(targetPath, 'utf8') : undefined\n if (existing === content) continue\n writeFileSync(targetPath, content, 'utf8')\n if (existing) {\n updated++\n } else {\n created++\n }\n }\n\n return {\n created, templateNames, updated,\n }\n}\n\nconst removeStaleCommands = (commandsDir: string, templateNames: Set<string>) => {\n const existingCommands = readdirSync(commandsDir).filter(f => f.startsWith(XYLABS_COMMANDS_PREFIX) && f.endsWith('.md'))\n let removed = 0\n\n for (const file of existingCommands) {\n if (!templateNames.has(file)) {\n unlinkSync(PATH.resolve(commandsDir, file))\n removed++\n }\n }\n\n return removed\n}\n\nconst removeLegacyCommands = (commandsDir: string): number => {\n const legacyFiles = readdirSync(commandsDir).filter(f => f.startsWith(LEGACY_COMMANDS_PREFIX) && f.endsWith('.md'))\n for (const file of legacyFiles) {\n unlinkSync(PATH.resolve(commandsDir, file))\n }\n return legacyFiles.length\n}\n\nconst logCommandsResult = (created: number, updated: number, removed: number) => {\n if (created || updated || removed) {\n const parts = [\n created ? `${created} created` : '',\n updated ? `${updated} updated` : '',\n removed ? `${removed} removed` : '',\n ].filter(Boolean)\n console.log(chalk.green(`.claude/commands/${XYLABS_COMMANDS_PREFIX}*.md: ${parts.join(', ')}`))\n } else {\n console.log(chalk.gray(`.claude/commands/${XYLABS_COMMANDS_PREFIX}*.md: already up to date`))\n }\n}\n\nexport const claudeCommands = (): number => {\n const cwd = INIT_CWD() ?? process.cwd()\n const commandsDir = PATH.resolve(cwd, '.claude', 'commands')\n\n mkdirSync(commandsDir, { recursive: true })\n\n const legacy = removeLegacyCommands(commandsDir)\n const {\n created, templateNames, updated,\n } = syncCommandFiles(commandsDir)\n const removed = removeStaleCommands(commandsDir, templateNames)\n logCommandsResult(created, updated, removed + legacy)\n\n return 0\n}\n","import { spawnSync } from 'node:child_process'\nimport {\n existsSync, mkdirSync, readdirSync, readFileSync, unlinkSync, writeFileSync,\n} from 'node:fs'\nimport PATH from 'node:path'\n\nimport chalk from 'chalk'\n\nimport {\n claudeMdLocalTemplate, claudeMdRuleTemplates, XYLABS_RULES_PREFIX,\n} from '../lib/index.ts'\nimport { INIT_CWD } from '../lib/yarn/index.ts'\n\nconst syncRuleFiles = (rulesDir: string) => {\n const templates = claudeMdRuleTemplates()\n const templateNames = new Set(Object.keys(templates))\n let updated = 0\n let created = 0\n\n for (const [filename, content] of Object.entries(templates)) {\n const targetPath = PATH.resolve(rulesDir, filename)\n const existing = existsSync(targetPath) ? readFileSync(targetPath, 'utf8') : undefined\n if (existing === content) continue\n writeFileSync(targetPath, content, 'utf8')\n if (existing) {\n updated++\n } else {\n created++\n }\n }\n\n return {\n created, templateNames, updated,\n }\n}\n\nconst removeStaleRules = (rulesDir: string, templateNames: Set<string>) => {\n const existingRules = readdirSync(rulesDir).filter(f => f.startsWith(XYLABS_RULES_PREFIX) && f.endsWith('.md'))\n let removed = 0\n\n for (const file of existingRules) {\n if (!templateNames.has(file)) {\n unlinkSync(PATH.resolve(rulesDir, file))\n removed++\n }\n }\n\n return removed\n}\n\nconst logRulesResult = (created: number, updated: number, removed: number) => {\n if (created || updated || removed) {\n const parts = [\n created ? `${created} created` : '',\n updated ? `${updated} updated` : '',\n removed ? `${removed} removed` : '',\n ].filter(Boolean)\n console.log(chalk.green(`.claude/rules/${XYLABS_RULES_PREFIX}*.md: ${parts.join(', ')}`))\n } else {\n console.log(chalk.gray(`.claude/rules/${XYLABS_RULES_PREFIX}*.md: already up to date`))\n }\n}\n\nconst ensureProjectClaudeMd = (cwd: string, force?: boolean) => {\n const projectPath = PATH.resolve(cwd, 'CLAUDE.md')\n\n if (!existsSync(projectPath) || force) {\n if (force && existsSync(projectPath)) {\n console.log(chalk.yellow('Regenerating CLAUDE.md'))\n }\n console.log(chalk.green('Generating CLAUDE.md via claude /init...'))\n const result = spawnSync('claude', ['-p', '/init', '--allowedTools', 'Read', 'Write', 'Glob', 'Grep'], {\n cwd,\n shell: true,\n stdio: 'inherit',\n })\n if (result.status !== 0) {\n console.error(chalk.red('claude /init failed — is Claude Code installed?'))\n return 1\n }\n } else {\n console.log(chalk.gray('CLAUDE.md already exists (skipped, use --force to regenerate)'))\n }\n return 0\n}\n\nconst ensureLocalClaudeMd = (cwd: string) => {\n const localPath = PATH.resolve(cwd, 'CLAUDE.local.md')\n\n if (existsSync(localPath)) {\n console.log(chalk.gray('CLAUDE.local.md already exists (skipped)'))\n } else {\n writeFileSync(localPath, claudeMdLocalTemplate(), 'utf8')\n console.log(chalk.green('Generated CLAUDE.local.md'))\n }\n}\n\nexport const claudeRules = ({ force }: { force?: boolean } = {}): number => {\n const cwd = INIT_CWD() ?? process.cwd()\n const rulesDir = PATH.resolve(cwd, '.claude', 'rules')\n\n mkdirSync(rulesDir, { recursive: true })\n\n const {\n created, templateNames, updated,\n } = syncRuleFiles(rulesDir)\n const removed = removeStaleRules(rulesDir, templateNames)\n logRulesResult(created, updated, removed)\n const claudeMdResult = ensureProjectClaudeMd(cwd, force)\n ensureLocalClaudeMd(cwd)\n\n return claudeMdResult ?? 0\n}\n","import {\n existsSync, mkdirSync, writeFileSync,\n} from 'node:fs'\nimport PATH from 'node:path'\nimport { createInterface } from 'node:readline'\n\nimport chalk from 'chalk'\n\nimport { INIT_CWD } from '../lib/yarn/index.ts'\n\nconst DEFAULT_SETTINGS = {\n permissions: {\n allow: [\n 'Bash(git *)',\n 'Bash(yarn *)',\n 'Bash(npx *)',\n 'Bash(node *)',\n 'Bash(ls *)',\n 'Bash(mkdir *)',\n 'Bash(cp *)',\n 'Bash(mv *)',\n 'Bash(rm *)',\n 'Bash(cat *)',\n 'Bash(head *)',\n 'Bash(tail *)',\n 'Bash(echo *)',\n 'Bash(pwd)',\n 'Bash(which *)',\n 'Bash(gh *)',\n 'Read',\n 'Edit',\n 'Write',\n 'Glob',\n 'Grep',\n 'Skill',\n ],\n deny: [\n 'Bash(git push --force*)',\n 'Bash(git reset --hard*)',\n 'Bash(rm -rf /*)',\n ],\n },\n}\n\nfunction askConfirmation(question: string): Promise<boolean> {\n const rl = createInterface({ input: process.stdin, output: process.stdout })\n return new Promise((resolve) => {\n rl.question(question, (answer) => {\n rl.close()\n resolve(answer.toLowerCase() === 'y' || answer.toLowerCase() === 'yes')\n })\n })\n}\n\nexport async function claudeSettings(): Promise<number> {\n const cwd = INIT_CWD() ?? process.cwd()\n const claudeDir = PATH.resolve(cwd, '.claude')\n const settingsPath = PATH.resolve(claudeDir, 'settings.local.json')\n\n mkdirSync(claudeDir, { recursive: true })\n\n if (existsSync(settingsPath)) {\n const confirmed = await askConfirmation(\n chalk.yellow(`${settingsPath} already exists. Replace it? (y/N) `),\n )\n if (!confirmed) {\n console.log(chalk.gray('Skipped — existing settings.local.json preserved'))\n return 0\n }\n }\n\n writeFileSync(settingsPath, `${JSON.stringify(DEFAULT_SETTINGS, null, 2)}\\n`, 'utf8')\n console.log(chalk.green('Generated .claude/settings.local.json'))\n return 0\n}\n","import type { CommandModule } from 'yargs'\n\nimport {\n claudeCommands, claudeRules, claudeSettings,\n} from '../../../actions/index.ts'\n\nexport const initCommand: CommandModule = {\n builder: (yargs) => {\n return yargs\n .option('force', {\n alias: 'f',\n default: false,\n description: 'Overwrite existing CLAUDE.md',\n type: 'boolean',\n })\n },\n command: 'init',\n describe: 'Initialize all Claude configuration (commands, rules, settings)',\n handler: async (argv) => {\n if (argv.verbose) console.log('Claude Init')\n const commandsResult = claudeCommands()\n const rulesResult = claudeRules({ force: argv.force as boolean | undefined })\n const settingsResult = await claudeSettings()\n process.exitCode = commandsResult || rulesResult || settingsResult\n },\n}\n"],"mappings":"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","names":["require","readdirSync","readFileSync","PATH","PATH","readFileSync","readdirSync","existsSync","mkdirSync","readdirSync","readFileSync","unlinkSync","writeFileSync","PATH","chalk","PATH","existsSync","readFileSync","writeFileSync","readdirSync","unlinkSync","chalk","mkdirSync","existsSync","mkdirSync","writeFileSync","PATH","chalk","PATH","mkdirSync","existsSync","chalk","writeFileSync"]}
|
|
@@ -19,7 +19,7 @@ var claudeMdRuleTemplates = () => {
|
|
|
19
19
|
}
|
|
20
20
|
return result;
|
|
21
21
|
};
|
|
22
|
-
var
|
|
22
|
+
var claudeMdLocalTemplate = () => readFileSync(PATH.resolve(templatesDir, "CLAUDE-local.md"), "utf8");
|
|
23
23
|
|
|
24
24
|
// src/lib/yarn/yarnInitCwd.ts
|
|
25
25
|
var INIT_CWD = () => {
|
|
@@ -28,6 +28,7 @@ var INIT_CWD = () => {
|
|
|
28
28
|
};
|
|
29
29
|
|
|
30
30
|
// src/actions/claude-rules.ts
|
|
31
|
+
import { spawnSync } from "child_process";
|
|
31
32
|
import {
|
|
32
33
|
existsSync,
|
|
33
34
|
mkdirSync,
|
|
@@ -87,12 +88,30 @@ var ensureProjectClaudeMd = (cwd, force) => {
|
|
|
87
88
|
const projectPath = PATH2.resolve(cwd, "CLAUDE.md");
|
|
88
89
|
if (!existsSync(projectPath) || force) {
|
|
89
90
|
if (force && existsSync(projectPath)) {
|
|
90
|
-
console.log(chalk.yellow("
|
|
91
|
+
console.log(chalk.yellow("Regenerating CLAUDE.md"));
|
|
92
|
+
}
|
|
93
|
+
console.log(chalk.green("Generating CLAUDE.md via claude /init..."));
|
|
94
|
+
const result = spawnSync("claude", ["-p", "/init", "--allowedTools", "Read", "Write", "Glob", "Grep"], {
|
|
95
|
+
cwd,
|
|
96
|
+
shell: true,
|
|
97
|
+
stdio: "inherit"
|
|
98
|
+
});
|
|
99
|
+
if (result.status !== 0) {
|
|
100
|
+
console.error(chalk.red("claude /init failed \u2014 is Claude Code installed?"));
|
|
101
|
+
return 1;
|
|
91
102
|
}
|
|
92
|
-
writeFileSync(projectPath, claudeMdProjectTemplate(), "utf8");
|
|
93
|
-
console.log(chalk.green("Generated CLAUDE.md"));
|
|
94
103
|
} else {
|
|
95
|
-
console.log(chalk.gray("CLAUDE.md already exists (skipped)"));
|
|
104
|
+
console.log(chalk.gray("CLAUDE.md already exists (skipped, use --force to regenerate)"));
|
|
105
|
+
}
|
|
106
|
+
return 0;
|
|
107
|
+
};
|
|
108
|
+
var ensureLocalClaudeMd = (cwd) => {
|
|
109
|
+
const localPath = PATH2.resolve(cwd, "CLAUDE.local.md");
|
|
110
|
+
if (existsSync(localPath)) {
|
|
111
|
+
console.log(chalk.gray("CLAUDE.local.md already exists (skipped)"));
|
|
112
|
+
} else {
|
|
113
|
+
writeFileSync(localPath, claudeMdLocalTemplate(), "utf8");
|
|
114
|
+
console.log(chalk.green("Generated CLAUDE.local.md"));
|
|
96
115
|
}
|
|
97
116
|
};
|
|
98
117
|
var claudeRules = ({ force } = {}) => {
|
|
@@ -106,8 +125,9 @@ var claudeRules = ({ force } = {}) => {
|
|
|
106
125
|
} = syncRuleFiles(rulesDir);
|
|
107
126
|
const removed = removeStaleRules(rulesDir, templateNames);
|
|
108
127
|
logRulesResult(created, updated, removed);
|
|
109
|
-
ensureProjectClaudeMd(cwd, force);
|
|
110
|
-
|
|
128
|
+
const claudeMdResult = ensureProjectClaudeMd(cwd, force);
|
|
129
|
+
ensureLocalClaudeMd(cwd);
|
|
130
|
+
return claudeMdResult ?? 0;
|
|
111
131
|
};
|
|
112
132
|
|
|
113
133
|
// src/xy/common/claude/rulesCommand.ts
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../../src/lib/claudeMdTemplate.ts","../../../../src/lib/yarn/yarnInitCwd.ts","../../../../src/actions/claude-rules.ts","../../../../src/xy/common/claude/rulesCommand.ts"],"sourcesContent":["import {\n readdirSync, readFileSync, statSync,\n} from 'node:fs'\nimport { createRequire } from 'node:module'\nimport PATH from 'node:path'\n\nconst require = createRequire(import.meta.url)\nconst packageRoot = PATH.dirname(require.resolve('@xylabs/ts-scripts-yarn3/package.json'))\nconst templatesDir = PATH.resolve(packageRoot, 'templates', 'claude')\n\nexport const XYLABS_RULES_PREFIX = 'xylabs-'\nexport const XYLABS_COMMANDS_PREFIX = 'xylabs-'\nexport const XYLABS_SKILLS_PREFIX = 'xylabs-'\n\nexport const claudeMdRuleTemplates = (): Record<string, string> => {\n const rulesDir = PATH.resolve(templatesDir, 'rules')\n const files = readdirSync(rulesDir).filter(f => f.startsWith(XYLABS_RULES_PREFIX) && f.endsWith('.md'))\n const result: Record<string, string> = {}\n for (const file of files) {\n result[file] = readFileSync(PATH.resolve(rulesDir, file), 'utf8')\n }\n return result\n}\n\nexport const claudeCommandTemplates = (): Record<string, string> => {\n const commandsDir = PATH.resolve(templatesDir, 'commands')\n const files = readdirSync(commandsDir).filter(f => f.startsWith(XYLABS_COMMANDS_PREFIX) && f.endsWith('.md'))\n const result: Record<string, string> = {}\n for (const file of files) {\n result[file] = readFileSync(PATH.resolve(commandsDir, file), 'utf8')\n }\n return result\n}\n\n// Returns { 'xylabs-foo': { 'SKILL.md': '...', 'other.ts': '...' } }\nexport const claudeSkillTemplates = (): Record<string, Record<string, string>> => {\n const skillsDir = PATH.resolve(templatesDir, 'skills')\n const dirs = readdirSync(skillsDir).filter(\n f => f.startsWith(XYLABS_SKILLS_PREFIX) && statSync(PATH.resolve(skillsDir, f)).isDirectory(),\n )\n const result: Record<string, Record<string, string>> = {}\n for (const dir of dirs) {\n const dirPath = PATH.resolve(skillsDir, dir)\n const files = readdirSync(dirPath, { recursive: true, encoding: 'utf8' }) as string[]\n result[dir] = {}\n for (const file of files) {\n if (statSync(PATH.resolve(dirPath, file)).isFile()) {\n result[dir][file] = readFileSync(PATH.resolve(dirPath, file), 'utf8')\n }\n }\n }\n return result\n}\n\nexport const claudeMdProjectTemplate = (): string =>\n readFileSync(PATH.resolve(templatesDir, 'CLAUDE-project.md'), 'utf8')\n","export const INIT_CWD = () => {\n if (!process.env.INIT_CWD) console.error('Missing INIT_CWD')\n return process.env.INIT_CWD\n}\n","import {\n existsSync, mkdirSync, readdirSync, readFileSync, unlinkSync, writeFileSync,\n} from 'node:fs'\nimport PATH from 'node:path'\n\nimport chalk from 'chalk'\n\nimport {\n claudeMdProjectTemplate, claudeMdRuleTemplates, XYLABS_RULES_PREFIX,\n} from '../lib/index.ts'\nimport { INIT_CWD } from '../lib/yarn/index.ts'\n\nconst syncRuleFiles = (rulesDir: string) => {\n const templates = claudeMdRuleTemplates()\n const templateNames = new Set(Object.keys(templates))\n let updated = 0\n let created = 0\n\n for (const [filename, content] of Object.entries(templates)) {\n const targetPath = PATH.resolve(rulesDir, filename)\n const existing = existsSync(targetPath) ? readFileSync(targetPath, 'utf8') : undefined\n if (existing === content) continue\n writeFileSync(targetPath, content, 'utf8')\n if (existing) {\n updated++\n } else {\n created++\n }\n }\n\n return {\n created, templateNames, updated,\n }\n}\n\nconst removeStaleRules = (rulesDir: string, templateNames: Set<string>) => {\n const existingRules = readdirSync(rulesDir).filter(f => f.startsWith(XYLABS_RULES_PREFIX) && f.endsWith('.md'))\n let removed = 0\n\n for (const file of existingRules) {\n if (!templateNames.has(file)) {\n unlinkSync(PATH.resolve(rulesDir, file))\n removed++\n }\n }\n\n return removed\n}\n\nconst logRulesResult = (created: number, updated: number, removed: number) => {\n if (created || updated || removed) {\n const parts = [\n created ? `${created} created` : '',\n updated ? `${updated} updated` : '',\n removed ? `${removed} removed` : '',\n ].filter(Boolean)\n console.log(chalk.green(`.claude/rules/${XYLABS_RULES_PREFIX}*.md: ${parts.join(', ')}`))\n } else {\n console.log(chalk.gray(`.claude/rules/${XYLABS_RULES_PREFIX}*.md: already up to date`))\n }\n}\n\nconst ensureProjectClaudeMd = (cwd: string, force?: boolean) => {\n const projectPath = PATH.resolve(cwd, 'CLAUDE.md')\n\n if (!existsSync(projectPath) || force) {\n if (force && existsSync(projectPath)) {\n console.log(chalk.yellow('Overwriting existing CLAUDE.md'))\n }\n writeFileSync(projectPath, claudeMdProjectTemplate(), 'utf8')\n console.log(chalk.green('Generated CLAUDE.md'))\n } else {\n console.log(chalk.gray('CLAUDE.md already exists (skipped)'))\n }\n}\n\nexport const claudeRules = ({ force }: { force?: boolean } = {}): number => {\n const cwd = INIT_CWD() ?? process.cwd()\n const rulesDir = PATH.resolve(cwd, '.claude', 'rules')\n\n mkdirSync(rulesDir, { recursive: true })\n\n const {\n created, templateNames, updated,\n } = syncRuleFiles(rulesDir)\n const removed = removeStaleRules(rulesDir, templateNames)\n logRulesResult(created, updated, removed)\n ensureProjectClaudeMd(cwd, force)\n\n return 0\n}\n","import type { CommandModule } from 'yargs'\n\nimport { claudeRules } from '../../../actions/index.ts'\n\nexport const rulesCommand: CommandModule = {\n builder: (yargs) => {\n return yargs\n .option('force', {\n alias: 'f',\n default: false,\n description: 'Overwrite existing CLAUDE.md',\n type: 'boolean',\n })\n },\n command: 'rules',\n describe: 'Sync XY Labs standard Claude rules to .claude/rules/',\n handler: (argv) => {\n if (argv.verbose) console.log('Claude Rules')\n process.exitCode = claudeRules({ force: argv.force as boolean | undefined })\n },\n}\n"],"mappings":"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","names":["require","readdirSync","readFileSync","PATH","PATH","readFileSync","readdirSync"]}
|
|
1
|
+
{"version":3,"sources":["../../../../src/lib/claudeMdTemplate.ts","../../../../src/lib/yarn/yarnInitCwd.ts","../../../../src/actions/claude-rules.ts","../../../../src/xy/common/claude/rulesCommand.ts"],"sourcesContent":["import {\n readdirSync, readFileSync, statSync,\n} from 'node:fs'\nimport { createRequire } from 'node:module'\nimport PATH from 'node:path'\n\nconst require = createRequire(import.meta.url)\nconst packageRoot = PATH.dirname(require.resolve('@xylabs/ts-scripts-yarn3/package.json'))\nconst templatesDir = PATH.resolve(packageRoot, 'templates', 'claude')\n\nexport const XYLABS_RULES_PREFIX = 'xylabs-'\nexport const XYLABS_COMMANDS_PREFIX = 'xy-'\nexport const LEGACY_COMMANDS_PREFIX = 'xylabs-'\nexport const XYLABS_SKILLS_PREFIX = 'xylabs-'\n\nexport const claudeMdRuleTemplates = (): Record<string, string> => {\n const rulesDir = PATH.resolve(templatesDir, 'rules')\n const files = readdirSync(rulesDir).filter(f => f.startsWith(XYLABS_RULES_PREFIX) && f.endsWith('.md'))\n const result: Record<string, string> = {}\n for (const file of files) {\n result[file] = readFileSync(PATH.resolve(rulesDir, file), 'utf8')\n }\n return result\n}\n\nexport const claudeCommandTemplates = (): Record<string, string> => {\n const commandsDir = PATH.resolve(templatesDir, 'commands')\n const files = readdirSync(commandsDir).filter(f => f.startsWith(XYLABS_COMMANDS_PREFIX) && f.endsWith('.md'))\n const result: Record<string, string> = {}\n for (const file of files) {\n result[file] = readFileSync(PATH.resolve(commandsDir, file), 'utf8')\n }\n return result\n}\n\n// Returns { 'xylabs-foo': { 'SKILL.md': '...', 'other.ts': '...' } }\nexport const claudeSkillTemplates = (): Record<string, Record<string, string>> => {\n const skillsDir = PATH.resolve(templatesDir, 'skills')\n const dirs = readdirSync(skillsDir).filter(\n f => f.startsWith(XYLABS_SKILLS_PREFIX) && statSync(PATH.resolve(skillsDir, f)).isDirectory(),\n )\n const result: Record<string, Record<string, string>> = {}\n for (const dir of dirs) {\n const dirPath = PATH.resolve(skillsDir, dir)\n const files = readdirSync(dirPath, { recursive: true, encoding: 'utf8' }) as string[]\n result[dir] = {}\n for (const file of files) {\n if (statSync(PATH.resolve(dirPath, file)).isFile()) {\n result[dir][file] = readFileSync(PATH.resolve(dirPath, file), 'utf8')\n }\n }\n }\n return result\n}\n\nexport const claudeMdProjectTemplate = (): string =>\n readFileSync(PATH.resolve(templatesDir, 'CLAUDE-project.md'), 'utf8')\n\nexport const claudeMdLocalTemplate = (): string =>\n readFileSync(PATH.resolve(templatesDir, 'CLAUDE-local.md'), 'utf8')\n","export const INIT_CWD = () => {\n if (!process.env.INIT_CWD) console.error('Missing INIT_CWD')\n return process.env.INIT_CWD\n}\n","import { spawnSync } from 'node:child_process'\nimport {\n existsSync, mkdirSync, readdirSync, readFileSync, unlinkSync, writeFileSync,\n} from 'node:fs'\nimport PATH from 'node:path'\n\nimport chalk from 'chalk'\n\nimport {\n claudeMdLocalTemplate, claudeMdRuleTemplates, XYLABS_RULES_PREFIX,\n} from '../lib/index.ts'\nimport { INIT_CWD } from '../lib/yarn/index.ts'\n\nconst syncRuleFiles = (rulesDir: string) => {\n const templates = claudeMdRuleTemplates()\n const templateNames = new Set(Object.keys(templates))\n let updated = 0\n let created = 0\n\n for (const [filename, content] of Object.entries(templates)) {\n const targetPath = PATH.resolve(rulesDir, filename)\n const existing = existsSync(targetPath) ? readFileSync(targetPath, 'utf8') : undefined\n if (existing === content) continue\n writeFileSync(targetPath, content, 'utf8')\n if (existing) {\n updated++\n } else {\n created++\n }\n }\n\n return {\n created, templateNames, updated,\n }\n}\n\nconst removeStaleRules = (rulesDir: string, templateNames: Set<string>) => {\n const existingRules = readdirSync(rulesDir).filter(f => f.startsWith(XYLABS_RULES_PREFIX) && f.endsWith('.md'))\n let removed = 0\n\n for (const file of existingRules) {\n if (!templateNames.has(file)) {\n unlinkSync(PATH.resolve(rulesDir, file))\n removed++\n }\n }\n\n return removed\n}\n\nconst logRulesResult = (created: number, updated: number, removed: number) => {\n if (created || updated || removed) {\n const parts = [\n created ? `${created} created` : '',\n updated ? `${updated} updated` : '',\n removed ? `${removed} removed` : '',\n ].filter(Boolean)\n console.log(chalk.green(`.claude/rules/${XYLABS_RULES_PREFIX}*.md: ${parts.join(', ')}`))\n } else {\n console.log(chalk.gray(`.claude/rules/${XYLABS_RULES_PREFIX}*.md: already up to date`))\n }\n}\n\nconst ensureProjectClaudeMd = (cwd: string, force?: boolean) => {\n const projectPath = PATH.resolve(cwd, 'CLAUDE.md')\n\n if (!existsSync(projectPath) || force) {\n if (force && existsSync(projectPath)) {\n console.log(chalk.yellow('Regenerating CLAUDE.md'))\n }\n console.log(chalk.green('Generating CLAUDE.md via claude /init...'))\n const result = spawnSync('claude', ['-p', '/init', '--allowedTools', 'Read', 'Write', 'Glob', 'Grep'], {\n cwd,\n shell: true,\n stdio: 'inherit',\n })\n if (result.status !== 0) {\n console.error(chalk.red('claude /init failed — is Claude Code installed?'))\n return 1\n }\n } else {\n console.log(chalk.gray('CLAUDE.md already exists (skipped, use --force to regenerate)'))\n }\n return 0\n}\n\nconst ensureLocalClaudeMd = (cwd: string) => {\n const localPath = PATH.resolve(cwd, 'CLAUDE.local.md')\n\n if (existsSync(localPath)) {\n console.log(chalk.gray('CLAUDE.local.md already exists (skipped)'))\n } else {\n writeFileSync(localPath, claudeMdLocalTemplate(), 'utf8')\n console.log(chalk.green('Generated CLAUDE.local.md'))\n }\n}\n\nexport const claudeRules = ({ force }: { force?: boolean } = {}): number => {\n const cwd = INIT_CWD() ?? process.cwd()\n const rulesDir = PATH.resolve(cwd, '.claude', 'rules')\n\n mkdirSync(rulesDir, { recursive: true })\n\n const {\n created, templateNames, updated,\n } = syncRuleFiles(rulesDir)\n const removed = removeStaleRules(rulesDir, templateNames)\n logRulesResult(created, updated, removed)\n const claudeMdResult = ensureProjectClaudeMd(cwd, force)\n ensureLocalClaudeMd(cwd)\n\n return claudeMdResult ?? 0\n}\n","import type { CommandModule } from 'yargs'\n\nimport { claudeRules } from '../../../actions/index.ts'\n\nexport const rulesCommand: CommandModule = {\n builder: (yargs) => {\n return yargs\n .option('force', {\n alias: 'f',\n default: false,\n description: 'Overwrite existing CLAUDE.md',\n type: 'boolean',\n })\n },\n command: 'rules',\n describe: 'Sync XY Labs standard Claude rules to .claude/rules/',\n handler: (argv) => {\n if (argv.verbose) console.log('Claude Rules')\n process.exitCode = claudeRules({ force: argv.force as boolean | undefined })\n },\n}\n"],"mappings":"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","names":["require","readdirSync","readFileSync","PATH","PATH","readFileSync","readdirSync"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../../src/lib/claudeMdTemplate.ts","../../../../src/lib/yarn/yarnInitCwd.ts","../../../../src/actions/claude-skills.ts","../../../../src/xy/common/claude/skillsCommand.ts"],"sourcesContent":["import {\n readdirSync, readFileSync, statSync,\n} from 'node:fs'\nimport { createRequire } from 'node:module'\nimport PATH from 'node:path'\n\nconst require = createRequire(import.meta.url)\nconst packageRoot = PATH.dirname(require.resolve('@xylabs/ts-scripts-yarn3/package.json'))\nconst templatesDir = PATH.resolve(packageRoot, 'templates', 'claude')\n\nexport const XYLABS_RULES_PREFIX = 'xylabs-'\nexport const XYLABS_COMMANDS_PREFIX = 'xylabs-'\nexport const XYLABS_SKILLS_PREFIX = 'xylabs-'\n\nexport const claudeMdRuleTemplates = (): Record<string, string> => {\n const rulesDir = PATH.resolve(templatesDir, 'rules')\n const files = readdirSync(rulesDir).filter(f => f.startsWith(XYLABS_RULES_PREFIX) && f.endsWith('.md'))\n const result: Record<string, string> = {}\n for (const file of files) {\n result[file] = readFileSync(PATH.resolve(rulesDir, file), 'utf8')\n }\n return result\n}\n\nexport const claudeCommandTemplates = (): Record<string, string> => {\n const commandsDir = PATH.resolve(templatesDir, 'commands')\n const files = readdirSync(commandsDir).filter(f => f.startsWith(XYLABS_COMMANDS_PREFIX) && f.endsWith('.md'))\n const result: Record<string, string> = {}\n for (const file of files) {\n result[file] = readFileSync(PATH.resolve(commandsDir, file), 'utf8')\n }\n return result\n}\n\n// Returns { 'xylabs-foo': { 'SKILL.md': '...', 'other.ts': '...' } }\nexport const claudeSkillTemplates = (): Record<string, Record<string, string>> => {\n const skillsDir = PATH.resolve(templatesDir, 'skills')\n const dirs = readdirSync(skillsDir).filter(\n f => f.startsWith(XYLABS_SKILLS_PREFIX) && statSync(PATH.resolve(skillsDir, f)).isDirectory(),\n )\n const result: Record<string, Record<string, string>> = {}\n for (const dir of dirs) {\n const dirPath = PATH.resolve(skillsDir, dir)\n const files = readdirSync(dirPath, { recursive: true, encoding: 'utf8' }) as string[]\n result[dir] = {}\n for (const file of files) {\n if (statSync(PATH.resolve(dirPath, file)).isFile()) {\n result[dir][file] = readFileSync(PATH.resolve(dirPath, file), 'utf8')\n }\n }\n }\n return result\n}\n\nexport const claudeMdProjectTemplate = (): string =>\n readFileSync(PATH.resolve(templatesDir, 'CLAUDE-project.md'), 'utf8')\n","export const INIT_CWD = () => {\n if (!process.env.INIT_CWD) console.error('Missing INIT_CWD')\n return process.env.INIT_CWD\n}\n","import {\n existsSync, mkdirSync, readdirSync, readFileSync, rmSync, statSync, writeFileSync,\n} from 'node:fs'\nimport PATH from 'node:path'\n\nimport chalk from 'chalk'\n\nimport { claudeSkillTemplates, XYLABS_SKILLS_PREFIX } from '../lib/index.ts'\nimport { INIT_CWD } from '../lib/yarn/index.ts'\n\nconst syncSkillFiles = (skillsDir: string) => {\n const templates = claudeSkillTemplates()\n const templateNames = new Set(Object.keys(templates))\n let updated = 0\n let created = 0\n\n for (const [skillName, files] of Object.entries(templates)) {\n const skillDir = PATH.resolve(skillsDir, skillName)\n mkdirSync(skillDir, { recursive: true })\n\n for (const [filename, content] of Object.entries(files)) {\n const targetPath = PATH.resolve(skillDir, filename)\n mkdirSync(PATH.dirname(targetPath), { recursive: true })\n const existing = existsSync(targetPath) ? readFileSync(targetPath, 'utf8') : undefined\n if (existing === content) continue\n writeFileSync(targetPath, content, 'utf8')\n if (existing) {\n updated++\n } else {\n created++\n }\n }\n }\n\n return {\n created, templateNames, updated,\n }\n}\n\nconst removeStaleSkills = (skillsDir: string, templateNames: Set<string>) => {\n const existingSkills = readdirSync(skillsDir).filter(\n f => f.startsWith(XYLABS_SKILLS_PREFIX) && statSync(PATH.resolve(skillsDir, f)).isDirectory(),\n )\n let removed = 0\n\n for (const dir of existingSkills) {\n if (!templateNames.has(dir)) {\n rmSync(PATH.resolve(skillsDir, dir), { recursive: true })\n removed++\n }\n }\n\n return removed\n}\n\nconst logSkillsResult = (created: number, updated: number, removed: number) => {\n if (created || updated || removed) {\n const parts = [\n created ? `${created} created` : '',\n updated ? `${updated} updated` : '',\n removed ? `${removed} removed` : '',\n ].filter(Boolean)\n console.log(chalk.green(`.claude/skills/${XYLABS_SKILLS_PREFIX}*/: ${parts.join(', ')}`))\n } else {\n console.log(chalk.gray(`.claude/skills/${XYLABS_SKILLS_PREFIX}*/: already up to date`))\n }\n}\n\nexport const claudeSkills = (): number => {\n const cwd = INIT_CWD() ?? process.cwd()\n const skillsDir = PATH.resolve(cwd, '.claude', 'skills')\n\n mkdirSync(skillsDir, { recursive: true })\n\n const {\n created, templateNames, updated,\n } = syncSkillFiles(skillsDir)\n const removed = removeStaleSkills(skillsDir, templateNames)\n logSkillsResult(created, updated, removed)\n\n return 0\n}\n","import type { CommandModule } from 'yargs'\n\nimport { claudeSkills } from '../../../actions/index.ts'\n\nexport const skillsCommand: CommandModule = {\n builder: yargs => yargs,\n command: 'skills',\n describe: 'Sync XY Labs standard Claude skills to .claude/skills/',\n handler: (argv) => {\n if (argv.verbose) console.log('Claude Skills')\n process.exitCode = claudeSkills()\n },\n}\n"],"mappings":";AAAA;AAAA,EACE;AAAA,EAAa;AAAA,EAAc;AAAA,OACtB;AACP,SAAS,qBAAqB;AAC9B,OAAO,UAAU;AAEjB,IAAMA,WAAU,cAAc,YAAY,GAAG;AAC7C,IAAM,cAAc,KAAK,QAAQA,SAAQ,QAAQ,uCAAuC,CAAC;AACzF,IAAM,eAAe,KAAK,QAAQ,aAAa,aAAa,QAAQ;
|
|
1
|
+
{"version":3,"sources":["../../../../src/lib/claudeMdTemplate.ts","../../../../src/lib/yarn/yarnInitCwd.ts","../../../../src/actions/claude-skills.ts","../../../../src/xy/common/claude/skillsCommand.ts"],"sourcesContent":["import {\n readdirSync, readFileSync, statSync,\n} from 'node:fs'\nimport { createRequire } from 'node:module'\nimport PATH from 'node:path'\n\nconst require = createRequire(import.meta.url)\nconst packageRoot = PATH.dirname(require.resolve('@xylabs/ts-scripts-yarn3/package.json'))\nconst templatesDir = PATH.resolve(packageRoot, 'templates', 'claude')\n\nexport const XYLABS_RULES_PREFIX = 'xylabs-'\nexport const XYLABS_COMMANDS_PREFIX = 'xy-'\nexport const LEGACY_COMMANDS_PREFIX = 'xylabs-'\nexport const XYLABS_SKILLS_PREFIX = 'xylabs-'\n\nexport const claudeMdRuleTemplates = (): Record<string, string> => {\n const rulesDir = PATH.resolve(templatesDir, 'rules')\n const files = readdirSync(rulesDir).filter(f => f.startsWith(XYLABS_RULES_PREFIX) && f.endsWith('.md'))\n const result: Record<string, string> = {}\n for (const file of files) {\n result[file] = readFileSync(PATH.resolve(rulesDir, file), 'utf8')\n }\n return result\n}\n\nexport const claudeCommandTemplates = (): Record<string, string> => {\n const commandsDir = PATH.resolve(templatesDir, 'commands')\n const files = readdirSync(commandsDir).filter(f => f.startsWith(XYLABS_COMMANDS_PREFIX) && f.endsWith('.md'))\n const result: Record<string, string> = {}\n for (const file of files) {\n result[file] = readFileSync(PATH.resolve(commandsDir, file), 'utf8')\n }\n return result\n}\n\n// Returns { 'xylabs-foo': { 'SKILL.md': '...', 'other.ts': '...' } }\nexport const claudeSkillTemplates = (): Record<string, Record<string, string>> => {\n const skillsDir = PATH.resolve(templatesDir, 'skills')\n const dirs = readdirSync(skillsDir).filter(\n f => f.startsWith(XYLABS_SKILLS_PREFIX) && statSync(PATH.resolve(skillsDir, f)).isDirectory(),\n )\n const result: Record<string, Record<string, string>> = {}\n for (const dir of dirs) {\n const dirPath = PATH.resolve(skillsDir, dir)\n const files = readdirSync(dirPath, { recursive: true, encoding: 'utf8' }) as string[]\n result[dir] = {}\n for (const file of files) {\n if (statSync(PATH.resolve(dirPath, file)).isFile()) {\n result[dir][file] = readFileSync(PATH.resolve(dirPath, file), 'utf8')\n }\n }\n }\n return result\n}\n\nexport const claudeMdProjectTemplate = (): string =>\n readFileSync(PATH.resolve(templatesDir, 'CLAUDE-project.md'), 'utf8')\n\nexport const claudeMdLocalTemplate = (): string =>\n readFileSync(PATH.resolve(templatesDir, 'CLAUDE-local.md'), 'utf8')\n","export const INIT_CWD = () => {\n if (!process.env.INIT_CWD) console.error('Missing INIT_CWD')\n return process.env.INIT_CWD\n}\n","import {\n existsSync, mkdirSync, readdirSync, readFileSync, rmSync, statSync, writeFileSync,\n} from 'node:fs'\nimport PATH from 'node:path'\n\nimport chalk from 'chalk'\n\nimport { claudeSkillTemplates, XYLABS_SKILLS_PREFIX } from '../lib/index.ts'\nimport { INIT_CWD } from '../lib/yarn/index.ts'\n\nconst syncSkillFiles = (skillsDir: string) => {\n const templates = claudeSkillTemplates()\n const templateNames = new Set(Object.keys(templates))\n let updated = 0\n let created = 0\n\n for (const [skillName, files] of Object.entries(templates)) {\n const skillDir = PATH.resolve(skillsDir, skillName)\n mkdirSync(skillDir, { recursive: true })\n\n for (const [filename, content] of Object.entries(files)) {\n const targetPath = PATH.resolve(skillDir, filename)\n mkdirSync(PATH.dirname(targetPath), { recursive: true })\n const existing = existsSync(targetPath) ? readFileSync(targetPath, 'utf8') : undefined\n if (existing === content) continue\n writeFileSync(targetPath, content, 'utf8')\n if (existing) {\n updated++\n } else {\n created++\n }\n }\n }\n\n return {\n created, templateNames, updated,\n }\n}\n\nconst removeStaleSkills = (skillsDir: string, templateNames: Set<string>) => {\n const existingSkills = readdirSync(skillsDir).filter(\n f => f.startsWith(XYLABS_SKILLS_PREFIX) && statSync(PATH.resolve(skillsDir, f)).isDirectory(),\n )\n let removed = 0\n\n for (const dir of existingSkills) {\n if (!templateNames.has(dir)) {\n rmSync(PATH.resolve(skillsDir, dir), { recursive: true })\n removed++\n }\n }\n\n return removed\n}\n\nconst logSkillsResult = (created: number, updated: number, removed: number) => {\n if (created || updated || removed) {\n const parts = [\n created ? `${created} created` : '',\n updated ? `${updated} updated` : '',\n removed ? `${removed} removed` : '',\n ].filter(Boolean)\n console.log(chalk.green(`.claude/skills/${XYLABS_SKILLS_PREFIX}*/: ${parts.join(', ')}`))\n } else {\n console.log(chalk.gray(`.claude/skills/${XYLABS_SKILLS_PREFIX}*/: already up to date`))\n }\n}\n\nexport const claudeSkills = (): number => {\n const cwd = INIT_CWD() ?? process.cwd()\n const skillsDir = PATH.resolve(cwd, '.claude', 'skills')\n\n mkdirSync(skillsDir, { recursive: true })\n\n const {\n created, templateNames, updated,\n } = syncSkillFiles(skillsDir)\n const removed = removeStaleSkills(skillsDir, templateNames)\n logSkillsResult(created, updated, removed)\n\n return 0\n}\n","import type { CommandModule } from 'yargs'\n\nimport { claudeSkills } from '../../../actions/index.ts'\n\nexport const skillsCommand: CommandModule = {\n builder: yargs => yargs,\n command: 'skills',\n describe: 'Sync XY Labs standard Claude skills to .claude/skills/',\n handler: (argv) => {\n if (argv.verbose) console.log('Claude Skills')\n process.exitCode = claudeSkills()\n },\n}\n"],"mappings":"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","names":["require","readdirSync","readFileSync","statSync","PATH","PATH","readFileSync","readdirSync","statSync"]}
|
|
@@ -0,0 +1,158 @@
|
|
|
1
|
+
// src/lib/file/constants.ts
|
|
2
|
+
var WINDOWS_NEWLINE_REGEX = /\r\n/g;
|
|
3
|
+
var CROSS_PLATFORM_NEWLINE = "\n";
|
|
4
|
+
|
|
5
|
+
// src/lib/file/fileLines.ts
|
|
6
|
+
import {
|
|
7
|
+
existsSync,
|
|
8
|
+
readFileSync,
|
|
9
|
+
writeFileSync
|
|
10
|
+
} from "fs";
|
|
11
|
+
|
|
12
|
+
// src/lib/string/empty.ts
|
|
13
|
+
var empty = (value) => value?.trim().length === 0;
|
|
14
|
+
var notEmpty = (value) => !empty(value);
|
|
15
|
+
|
|
16
|
+
// src/lib/string/union.ts
|
|
17
|
+
var union = (a, b) => /* @__PURE__ */ new Set([...new Set(a), ...new Set(b)]);
|
|
18
|
+
|
|
19
|
+
// src/lib/file/ReadFileSyncOptions.ts
|
|
20
|
+
var defaultReadFileSyncOptions = { encoding: "utf8" };
|
|
21
|
+
|
|
22
|
+
// src/lib/file/fileLines.ts
|
|
23
|
+
var readLines = (uri, options = defaultReadFileSyncOptions) => existsSync(uri) ? readFileSync(uri, options).replace(WINDOWS_NEWLINE_REGEX, CROSS_PLATFORM_NEWLINE).split(CROSS_PLATFORM_NEWLINE) : [];
|
|
24
|
+
var readNonEmptyLines = (uri, options = defaultReadFileSyncOptions) => readLines(uri, options).filter(notEmpty);
|
|
25
|
+
var writeLines = (uri, lines, options = defaultReadFileSyncOptions) => {
|
|
26
|
+
const existing = existsSync(uri) ? readFileSync(uri, options) : void 0;
|
|
27
|
+
const desired = lines.join(CROSS_PLATFORM_NEWLINE);
|
|
28
|
+
if (existing !== desired) writeFileSync(uri, desired, options);
|
|
29
|
+
};
|
|
30
|
+
|
|
31
|
+
// src/lib/yarn/workspace/yarnWorkspaces.ts
|
|
32
|
+
import { spawnSync } from "child_process";
|
|
33
|
+
var yarnWorkspaces = () => {
|
|
34
|
+
const result = spawnSync("yarn", ["workspaces", "list", "--json", "--recursive"], { encoding: "utf8", shell: true });
|
|
35
|
+
if (result.error) {
|
|
36
|
+
throw result.error;
|
|
37
|
+
}
|
|
38
|
+
return result.stdout.toString().split("\n").slice(0, -1).map((item) => {
|
|
39
|
+
return JSON.parse(item);
|
|
40
|
+
});
|
|
41
|
+
};
|
|
42
|
+
|
|
43
|
+
// src/lib/yarn/yarnInitCwd.ts
|
|
44
|
+
var INIT_CWD = () => {
|
|
45
|
+
if (!process.env.INIT_CWD) console.error("Missing INIT_CWD");
|
|
46
|
+
return process.env.INIT_CWD;
|
|
47
|
+
};
|
|
48
|
+
|
|
49
|
+
// src/lib/gitignoreTemplate.ts
|
|
50
|
+
import { readFileSync as readFileSync2 } from "fs";
|
|
51
|
+
import { createRequire } from "module";
|
|
52
|
+
import PATH from "path";
|
|
53
|
+
var require2 = createRequire(import.meta.url);
|
|
54
|
+
var packageRoot = PATH.dirname(require2.resolve("@xylabs/ts-scripts-yarn3/package.json"));
|
|
55
|
+
var templatesDir = PATH.resolve(packageRoot, "templates", "gitignore");
|
|
56
|
+
var gitignoreTemplate = () => readFileSync2(PATH.resolve(templatesDir, "template.gitignore"), "utf8");
|
|
57
|
+
|
|
58
|
+
// src/actions/gitignore.ts
|
|
59
|
+
import { unlinkSync } from "fs";
|
|
60
|
+
import chalk from "chalk";
|
|
61
|
+
var COMMENT_PREFIX = "#";
|
|
62
|
+
var isComment = (line) => line.startsWith(COMMENT_PREFIX);
|
|
63
|
+
var isNegation = (line) => line.startsWith("!");
|
|
64
|
+
function parseTemplateSections(lines) {
|
|
65
|
+
const sections = [];
|
|
66
|
+
let current = [];
|
|
67
|
+
for (const line of lines) {
|
|
68
|
+
if (isComment(line)) {
|
|
69
|
+
if (current.length > 0) {
|
|
70
|
+
sections.push(current);
|
|
71
|
+
}
|
|
72
|
+
current = [line];
|
|
73
|
+
} else {
|
|
74
|
+
current.push(line);
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
if (current.length > 0) {
|
|
78
|
+
sections.push(current);
|
|
79
|
+
}
|
|
80
|
+
return sections;
|
|
81
|
+
}
|
|
82
|
+
function mergeWithTemplate(existing, templateContent) {
|
|
83
|
+
const templateLines = templateContent.split("\n").filter((line) => line.trim().length > 0);
|
|
84
|
+
const sections = parseTemplateSections(templateLines);
|
|
85
|
+
const existingEntries = new Set(existing.filter((line) => !isComment(line)));
|
|
86
|
+
const templateEntries = new Set(templateLines.filter((line) => !isComment(line)));
|
|
87
|
+
const customEntries = [...existingEntries].filter((entry) => !templateEntries.has(entry));
|
|
88
|
+
const result = [];
|
|
89
|
+
for (const section of sections) {
|
|
90
|
+
for (const line of section) {
|
|
91
|
+
result.push(line);
|
|
92
|
+
}
|
|
93
|
+
result.push("");
|
|
94
|
+
}
|
|
95
|
+
if (customEntries.length > 0) {
|
|
96
|
+
result.push("# Custom");
|
|
97
|
+
const sorted = [...union(customEntries, [])].toSorted((a, b) => {
|
|
98
|
+
if (isNegation(a) && !isNegation(b)) return 1;
|
|
99
|
+
if (!isNegation(a) && isNegation(b)) return -1;
|
|
100
|
+
return a.localeCompare(b);
|
|
101
|
+
});
|
|
102
|
+
for (const entry of sorted) {
|
|
103
|
+
result.push(entry);
|
|
104
|
+
}
|
|
105
|
+
result.push("");
|
|
106
|
+
}
|
|
107
|
+
return result;
|
|
108
|
+
}
|
|
109
|
+
function removePackageGitignores(cwd) {
|
|
110
|
+
let removed = 0;
|
|
111
|
+
const workspaces = yarnWorkspaces();
|
|
112
|
+
for (const { location } of workspaces) {
|
|
113
|
+
if (location === ".") continue;
|
|
114
|
+
const filePath = `${cwd}/${location}/.gitignore`;
|
|
115
|
+
try {
|
|
116
|
+
unlinkSync(filePath);
|
|
117
|
+
console.log(chalk.yellow(` Removed ${location}/.gitignore`));
|
|
118
|
+
removed++;
|
|
119
|
+
} catch {
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
return removed;
|
|
123
|
+
}
|
|
124
|
+
function gitignore() {
|
|
125
|
+
console.log(chalk.green("Generate .gitignore"));
|
|
126
|
+
const cwd = INIT_CWD() ?? ".";
|
|
127
|
+
const gitignorePath = `${cwd}/.gitignore`;
|
|
128
|
+
try {
|
|
129
|
+
const templateContent = gitignoreTemplate();
|
|
130
|
+
const existing = readNonEmptyLines(gitignorePath);
|
|
131
|
+
const merged = mergeWithTemplate(existing, templateContent);
|
|
132
|
+
writeLines(gitignorePath, merged);
|
|
133
|
+
console.log(chalk.green(" Root .gitignore updated"));
|
|
134
|
+
const removed = removePackageGitignores(cwd);
|
|
135
|
+
if (removed > 0) {
|
|
136
|
+
console.log(chalk.green(` Removed ${removed} package .gitignore file(s)`));
|
|
137
|
+
}
|
|
138
|
+
return 0;
|
|
139
|
+
} catch (ex) {
|
|
140
|
+
const error = ex;
|
|
141
|
+
console.error(chalk.red(`Generate .gitignore failed: ${error.message}`));
|
|
142
|
+
return 1;
|
|
143
|
+
}
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
// src/xy/common/gitignoreCommand.ts
|
|
147
|
+
var gitignoreCommand = {
|
|
148
|
+
command: "gitignore",
|
|
149
|
+
describe: "GitIgnore - Generate root .gitignore and remove package .gitignore files",
|
|
150
|
+
handler: (argv) => {
|
|
151
|
+
if (argv.verbose) console.log("GitIgnore");
|
|
152
|
+
process.exitCode = gitignore();
|
|
153
|
+
}
|
|
154
|
+
};
|
|
155
|
+
export {
|
|
156
|
+
gitignoreCommand
|
|
157
|
+
};
|
|
158
|
+
//# sourceMappingURL=gitignoreCommand.mjs.map
|