agent-directives 0.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 (57) hide show
  1. package/README.md +385 -0
  2. package/directives/adaptive-routing.md +361 -0
  3. package/directives/architecture-boundaries.md +223 -0
  4. package/directives/codebase-navigation.md +325 -0
  5. package/directives/context-handoff.md +220 -0
  6. package/directives/error-memory.md +169 -0
  7. package/directives/exploration-mode.md +266 -0
  8. package/directives/session-decisions.md +193 -0
  9. package/directives/specification-driven-development.md +278 -0
  10. package/directives/task-framing.md +154 -0
  11. package/directives/test-driven-development.md +305 -0
  12. package/directives/type-driven-development.md +173 -0
  13. package/directives/verification.md +266 -0
  14. package/directives/workspace-isolation.md +219 -0
  15. package/dist/cli.d.ts +3 -0
  16. package/dist/cli.d.ts.map +1 -0
  17. package/dist/cli.js +232 -0
  18. package/dist/cli.js.map +1 -0
  19. package/dist/context-audit.d.ts +30 -0
  20. package/dist/context-audit.d.ts.map +1 -0
  21. package/dist/context-audit.js +75 -0
  22. package/dist/context-audit.js.map +1 -0
  23. package/dist/install.d.ts +18 -0
  24. package/dist/install.d.ts.map +1 -0
  25. package/dist/install.js +28 -0
  26. package/dist/install.js.map +1 -0
  27. package/dist/manifest.d.ts +25 -0
  28. package/dist/manifest.d.ts.map +1 -0
  29. package/dist/manifest.js +29 -0
  30. package/dist/manifest.js.map +1 -0
  31. package/dist/prompt.d.ts +3 -0
  32. package/dist/prompt.d.ts.map +1 -0
  33. package/dist/prompt.js +29 -0
  34. package/dist/prompt.js.map +1 -0
  35. package/dist/targets.d.ts +10 -0
  36. package/dist/targets.d.ts.map +1 -0
  37. package/dist/targets.js +32 -0
  38. package/dist/targets.js.map +1 -0
  39. package/manifest.json +387 -0
  40. package/package.json +74 -0
  41. package/skills/architecture-boundary-reviewer/SKILL.md +228 -0
  42. package/skills/code-reviewer/SKILL.md +77 -0
  43. package/skills/codebase-health-reviewer/SKILL.md +234 -0
  44. package/skills/harness-hooks-reviewer/SKILL.md +159 -0
  45. package/skills/implementation-task-planner/SKILL.md +205 -0
  46. package/skills/mcp-integration-reviewer/SKILL.md +157 -0
  47. package/skills/product-requirements-writer/SKILL.md +205 -0
  48. package/skills/production-readiness-reviewer/SKILL.md +240 -0
  49. package/skills/self-audit/SKILL.md +134 -0
  50. package/skills/spec-reviewer/SKILL.md +304 -0
  51. package/skills/subagent-driven-development/SKILL.md +236 -0
  52. package/skills/systematic-debugging/SKILL.md +313 -0
  53. package/skills/test-reviewer/SKILL.md +293 -0
  54. package/templates/AGENTS.md +120 -0
  55. package/templates/CLAUDE.md +115 -0
  56. package/templates/copilot-instructions.md +116 -0
  57. package/templates/decision-log.md +44 -0
package/dist/cli.js ADDED
@@ -0,0 +1,232 @@
1
+ #!/usr/bin/env node
2
+ import { readFileSync } from 'node:fs';
3
+ import { join } from 'node:path';
4
+ import { Command } from 'commander';
5
+ import { buildContextAudit, renderContextAudit } from './context-audit.js';
6
+ import { filterEntries, findEntry, loadManifest, packageRoot } from './manifest.js';
7
+ import { installEntry, isEntryInstalled } from './install.js';
8
+ import { selectMultiple } from './prompt.js';
9
+ import { KNOWN_TOOLS, detectTool, isTool } from './targets.js';
10
+ const pkg = JSON.parse(readFileSync(join(packageRoot, 'package.json'), 'utf8'));
11
+ const DECIMAL_RADIX = 10;
12
+ const MIN_UNDERLINE_WIDTH = 4;
13
+ const ID_COLUMN_WIDTH = 34;
14
+ const TYPE_COLUMN_WIDTH = 10;
15
+ function resolveTool(provided) {
16
+ if (provided) {
17
+ if (!isTool(provided)) {
18
+ console.error(`Unknown tool '${provided}'. Expected one of: ${KNOWN_TOOLS.join(', ')}`);
19
+ process.exit(1);
20
+ }
21
+ return provided;
22
+ }
23
+ const detected = detectTool(process.cwd());
24
+ if (!detected) {
25
+ console.error(`Unable to auto-detect tool from current directory.`);
26
+ console.error(`Use --tool with one of: ${KNOWN_TOOLS.join(', ')}`);
27
+ process.exit(1);
28
+ }
29
+ return detected;
30
+ }
31
+ function reportInstall(entry, result) {
32
+ switch (result.status) {
33
+ case 'installed':
34
+ console.log(` ✓ ${entry.id}`);
35
+ break;
36
+ case 'skipped-identical':
37
+ console.log(` = ${entry.id} (already up-to-date)`);
38
+ break;
39
+ case 'skipped-conflict':
40
+ console.error(` ✗ ${entry.id} (conflict: ${result.path})`);
41
+ break;
42
+ }
43
+ }
44
+ function parseIntegerOption(value, opts) {
45
+ const { flag, minimum } = opts;
46
+ if (!/^[+-]?\d+$/.test(value)) {
47
+ console.error(`Invalid ${flag} '${value}'. Expected an integer.`);
48
+ process.exit(1);
49
+ }
50
+ const parsed = Number.parseInt(value, DECIMAL_RADIX);
51
+ if (!Number.isSafeInteger(parsed) || parsed < minimum) {
52
+ console.error(`Invalid ${flag} '${value}'. Expected an integer >= ${minimum}.`);
53
+ process.exit(1);
54
+ }
55
+ return parsed;
56
+ }
57
+ const program = new Command();
58
+ program
59
+ .name('agent-directives')
60
+ .description('Install agent directives and skills into your project')
61
+ .version(pkg.version);
62
+ function validateListOptions(opts) {
63
+ if (opts.type && opts.type !== 'directive' && opts.type !== 'skill') {
64
+ console.error(`Invalid --type '${opts.type}'. Expected 'directive' or 'skill'.`);
65
+ process.exit(1);
66
+ }
67
+ if (opts.tool && !isTool(opts.tool)) {
68
+ console.error(`Unknown tool '${opts.tool}'. Expected one of: ${KNOWN_TOOLS.join(', ')}`);
69
+ process.exit(1);
70
+ }
71
+ }
72
+ function groupByCategory(entries) {
73
+ const byCategory = new Map();
74
+ for (const entry of entries) {
75
+ const bucket = byCategory.get(entry.category) ?? [];
76
+ bucket.push(entry);
77
+ byCategory.set(entry.category, bucket);
78
+ }
79
+ return byCategory;
80
+ }
81
+ function printCategory(category, entries) {
82
+ console.log(`\n${category}`);
83
+ console.log('─'.repeat(Math.max(category.length, MIN_UNDERLINE_WIDTH)));
84
+ for (const entry of entries.sort((a, b) => a.id.localeCompare(b.id))) {
85
+ const marker = entry.required ? '★' : ' ';
86
+ console.log(` ${marker} ${entry.id.padEnd(ID_COLUMN_WIDTH)} ${entry.type.padEnd(TYPE_COLUMN_WIDTH)} ${entry.description}`);
87
+ }
88
+ }
89
+ program
90
+ .command('list')
91
+ .description('List available directives and skills')
92
+ .option('-c, --category <category>', 'Filter by category')
93
+ .option('-r, --required', 'Only show required entries')
94
+ .option('-t, --tool <tool>', `Filter by tool (${KNOWN_TOOLS.join(', ')})`)
95
+ .option('--type <type>', 'Filter by type (directive or skill)')
96
+ .action((opts) => {
97
+ validateListOptions(opts);
98
+ const manifest = loadManifest();
99
+ const filtered = filterEntries(manifest.entries, {
100
+ category: opts.category,
101
+ required: opts.required,
102
+ tool: opts.tool,
103
+ type: opts.type,
104
+ });
105
+ if (filtered.length === 0) {
106
+ console.log('No entries match the filters.');
107
+ return;
108
+ }
109
+ const byCategory = groupByCategory(filtered);
110
+ for (const [category, entries] of [...byCategory.entries()].sort(([a], [b]) => a.localeCompare(b))) {
111
+ printCategory(category, entries);
112
+ }
113
+ console.log(`\n${filtered.length} entr${filtered.length === 1 ? 'y' : 'ies'} (★ = required)`);
114
+ });
115
+ program
116
+ .command('context-audit')
117
+ .description('Estimate prompt weight for directives and skills')
118
+ .option('-t, --tool <tool>', `Filter by target tool (${KNOWN_TOOLS.join(', ')})`)
119
+ .option('-r, --required', 'Only include always-loaded required entries')
120
+ .option('--max-tokens <tokens>', 'Fail when the estimated token count exceeds this budget')
121
+ .option('--largest <count>', 'Number of largest entries to show', '10')
122
+ .action((opts) => {
123
+ if (opts.tool && !isTool(opts.tool)) {
124
+ console.error(`Unknown tool '${opts.tool}'. Expected one of: ${KNOWN_TOOLS.join(', ')}`);
125
+ process.exit(1);
126
+ }
127
+ const maxTokens = opts.maxTokens === undefined ? undefined : parseIntegerOption(opts.maxTokens, { flag: '--max-tokens', minimum: 0 });
128
+ const largest = opts.largest === undefined ? undefined : parseIntegerOption(opts.largest, { flag: '--largest', minimum: 1 });
129
+ const manifest = loadManifest();
130
+ const result = buildContextAudit(manifest.entries, {
131
+ tool: opts.tool,
132
+ requiredOnly: opts.required,
133
+ maxTokens,
134
+ largest,
135
+ });
136
+ const rendered = renderContextAudit(result);
137
+ if (result.overBudget) {
138
+ console.error(rendered);
139
+ console.error(`Context budget exceeded: ${result.estimatedTokens.toLocaleString()} > ${result.maxTokens?.toLocaleString()} tokens.`);
140
+ process.exit(1);
141
+ }
142
+ console.log(rendered);
143
+ });
144
+ program
145
+ .command('add <id>')
146
+ .description('Install a single directive or skill into the current project')
147
+ .option('-t, --tool <tool>', `Target tool (${KNOWN_TOOLS.join(', ')})`)
148
+ .option('-f, --force', 'Overwrite an existing file with different content')
149
+ .action((id, opts) => {
150
+ const manifest = loadManifest();
151
+ const entry = findEntry(manifest.entries, id);
152
+ if (!entry) {
153
+ console.error(`No such entry: ${id}`);
154
+ console.error(`Run 'agent-directives list' to see available entries.`);
155
+ process.exit(1);
156
+ }
157
+ const tool = resolveTool(opts.tool);
158
+ if (!entry.tools.includes(tool)) {
159
+ console.error(`Entry '${id}' does not support tool '${tool}' (supports: ${entry.tools.join(', ')}).`);
160
+ process.exit(1);
161
+ }
162
+ const result = installEntry(entry, { cwd: process.cwd(), tool, force: opts.force });
163
+ reportInstall(entry, result);
164
+ if (result.status === 'skipped-conflict') {
165
+ console.error(`Use --force to overwrite.`);
166
+ process.exit(1);
167
+ }
168
+ });
169
+ program
170
+ .command('check')
171
+ .description('Report missing required directives and skills for the target tool')
172
+ .option('-t, --tool <tool>', `Target tool (${KNOWN_TOOLS.join(', ')})`)
173
+ .action((opts) => {
174
+ const manifest = loadManifest();
175
+ const tool = resolveTool(opts.tool);
176
+ const required = filterEntries(manifest.entries, { required: true, tool });
177
+ const missing = required.filter((entry) => !isEntryInstalled(entry, { tool, cwd: process.cwd() }));
178
+ if (missing.length === 0) {
179
+ console.log(`✓ All ${required.length} required entries are installed for ${tool}.`);
180
+ return;
181
+ }
182
+ console.error(`✗ Missing ${missing.length} of ${required.length} required entries for ${tool}:`);
183
+ for (const entry of missing) {
184
+ console.error(` - ${entry.id} (${entry.type}, category: ${entry.category})`);
185
+ }
186
+ console.error(`\nRun 'agent-directives sync --tool ${tool}' to install them.`);
187
+ process.exit(1);
188
+ });
189
+ program
190
+ .command('sync')
191
+ .description('Install all required entries and prompt for optional categories')
192
+ .option('-t, --tool <tool>', `Target tool (${KNOWN_TOOLS.join(', ')})`)
193
+ .option('-y, --yes', 'Skip prompts; install required entries only')
194
+ .option('-f, --force', 'Overwrite files with different content')
195
+ .action(async (opts) => {
196
+ const manifest = loadManifest();
197
+ const tool = resolveTool(opts.tool);
198
+ const required = filterEntries(manifest.entries, { required: true, tool });
199
+ const optional = filterEntries(manifest.entries, { required: false, tool });
200
+ console.log(`Tool: ${tool}`);
201
+ console.log(`Installing ${required.length} required entr${required.length === 1 ? 'y' : 'ies'}...`);
202
+ const summary = { installed: 0, identical: 0, conflict: 0 };
203
+ const apply = (entries) => {
204
+ for (const entry of entries) {
205
+ const result = installEntry(entry, { cwd: process.cwd(), tool, force: opts.force });
206
+ reportInstall(entry, result);
207
+ if (result.status === 'installed')
208
+ summary.installed += 1;
209
+ else if (result.status === 'skipped-identical')
210
+ summary.identical += 1;
211
+ else
212
+ summary.conflict += 1;
213
+ }
214
+ };
215
+ apply(required);
216
+ if (!opts.yes && optional.length > 0) {
217
+ const categories = [...new Set(optional.map((entry) => entry.category))].sort();
218
+ const chosen = await selectMultiple('\nOptional categories:', categories);
219
+ const toInstall = optional.filter((entry) => chosen.includes(entry.category));
220
+ if (toInstall.length > 0) {
221
+ console.log(`\nInstalling ${toInstall.length} optional entr${toInstall.length === 1 ? 'y' : 'ies'}...`);
222
+ apply(toInstall);
223
+ }
224
+ }
225
+ console.log(`\nSummary: ${summary.installed} installed, ${summary.identical} already up-to-date, ${summary.conflict} conflicts`);
226
+ if (summary.conflict > 0 && !opts.force) {
227
+ console.error(`Re-run with --force to overwrite conflicting files.`);
228
+ process.exit(1);
229
+ }
230
+ });
231
+ await program.parseAsync(process.argv);
232
+ //# sourceMappingURL=cli.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,30 @@
1
+ import { type ManifestEntry } from './manifest.js';
2
+ export interface ContextAuditOptions {
3
+ tool?: string;
4
+ requiredOnly?: boolean;
5
+ maxTokens?: number;
6
+ largest?: number;
7
+ }
8
+ export interface ContextAuditEntry {
9
+ id: string;
10
+ type: ManifestEntry['type'];
11
+ path: string;
12
+ required: boolean;
13
+ category: string;
14
+ bytes: number;
15
+ estimatedTokens: number;
16
+ }
17
+ export interface ContextAuditResult {
18
+ tool?: string;
19
+ entries: ContextAuditEntry[];
20
+ totalBytes: number;
21
+ estimatedTokens: number;
22
+ requiredEntries: number;
23
+ optionalEntries: number;
24
+ largestEntries: ContextAuditEntry[];
25
+ maxTokens?: number;
26
+ overBudget: boolean;
27
+ }
28
+ export declare function buildContextAudit(entries: ManifestEntry[], options?: ContextAuditOptions): ContextAuditResult;
29
+ export declare function renderContextAudit(result: ContextAuditResult): string;
30
+ //# sourceMappingURL=context-audit.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"context-audit.d.ts","sourceRoot":"","sources":["../src/context-audit.ts"],"names":[],"mappings":"AAEA,OAAO,EAA8B,KAAK,aAAa,EAAE,MAAM,eAAe,CAAC;AAE/E,MAAM,WAAW,mBAAmB;IAClC,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,iBAAiB;IAChC,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,aAAa,CAAC,MAAM,CAAC,CAAC;IAC5B,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,OAAO,CAAC;IAClB,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,EAAE,MAAM,CAAC;IACd,eAAe,EAAE,MAAM,CAAC;CACzB;AAED,MAAM,WAAW,kBAAkB;IACjC,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,OAAO,EAAE,iBAAiB,EAAE,CAAC;IAC7B,UAAU,EAAE,MAAM,CAAC;IACnB,eAAe,EAAE,MAAM,CAAC;IACxB,eAAe,EAAE,MAAM,CAAC;IACxB,eAAe,EAAE,MAAM,CAAC;IACxB,cAAc,EAAE,iBAAiB,EAAE,CAAC;IACpC,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,UAAU,EAAE,OAAO,CAAC;CACrB;AA8BD,wBAAgB,iBAAiB,CAAC,OAAO,EAAE,aAAa,EAAE,EAAE,OAAO,GAAE,mBAAwB,GAAG,kBAAkB,CA2BjH;AAED,wBAAgB,kBAAkB,CAAC,MAAM,EAAE,kBAAkB,GAAG,MAAM,CAoBrE"}
@@ -0,0 +1,75 @@
1
+ import { readFileSync } from 'node:fs';
2
+ import { join } from 'node:path';
3
+ import { filterEntries, packageRoot } from './manifest.js';
4
+ const DEFAULT_LARGEST_COUNT = 10;
5
+ const TOKEN_CHARS = 4;
6
+ function estimateTokens(text) {
7
+ return Math.ceil(text.length / TOKEN_CHARS);
8
+ }
9
+ function auditEntry(entry) {
10
+ let content;
11
+ try {
12
+ content = readFileSync(join(packageRoot, entry.path), 'utf8');
13
+ }
14
+ catch (error) {
15
+ const reason = error instanceof Error ? error.message : String(error);
16
+ const wrappedError = new Error(`Failed to read manifest entry '${entry.id}' at '${entry.path}': ${reason}`);
17
+ wrappedError.cause = error;
18
+ throw wrappedError;
19
+ }
20
+ return {
21
+ id: entry.id,
22
+ type: entry.type,
23
+ path: entry.path,
24
+ required: entry.required,
25
+ category: entry.category,
26
+ bytes: Buffer.byteLength(content, 'utf8'),
27
+ estimatedTokens: estimateTokens(content),
28
+ };
29
+ }
30
+ export function buildContextAudit(entries, options = {}) {
31
+ const filtered = filterEntries(entries, {
32
+ tool: options.tool,
33
+ required: options.requiredOnly ? true : undefined,
34
+ });
35
+ const audited = filtered.map(auditEntry).sort((a, b) => a.id.localeCompare(b.id));
36
+ const totalBytes = audited.reduce((sum, entry) => sum + entry.bytes, 0);
37
+ const estimatedTokens = audited.reduce((sum, entry) => sum + entry.estimatedTokens, 0);
38
+ const largestCount = options.largest ?? DEFAULT_LARGEST_COUNT;
39
+ const largestEntries = [...audited]
40
+ .sort((a, b) => {
41
+ const tokenDelta = b.estimatedTokens - a.estimatedTokens;
42
+ return tokenDelta === 0 ? a.id.localeCompare(b.id) : tokenDelta;
43
+ })
44
+ .slice(0, largestCount);
45
+ return {
46
+ tool: options.tool,
47
+ entries: audited,
48
+ totalBytes,
49
+ estimatedTokens,
50
+ requiredEntries: audited.filter((entry) => entry.required).length,
51
+ optionalEntries: audited.filter((entry) => !entry.required).length,
52
+ largestEntries,
53
+ maxTokens: options.maxTokens,
54
+ overBudget: options.maxTokens !== undefined && estimatedTokens > options.maxTokens,
55
+ };
56
+ }
57
+ export function renderContextAudit(result) {
58
+ const scope = result.tool ? ` for ${result.tool}` : '';
59
+ const lines = [
60
+ `Context audit${scope}`,
61
+ `Estimated prompt tokens: ${result.estimatedTokens.toLocaleString()} (${result.totalBytes.toLocaleString()} bytes)`,
62
+ `Always-loaded entries: ${result.requiredEntries}`,
63
+ `Lazy/optional entries: ${result.optionalEntries}`,
64
+ ];
65
+ if (result.maxTokens !== undefined) {
66
+ lines.push(`Budget: ${result.maxTokens.toLocaleString()} tokens — ${result.overBudget ? 'FAIL' : 'PASS'}`);
67
+ }
68
+ lines.push('', 'Largest entries:');
69
+ for (const entry of result.largestEntries) {
70
+ const load = entry.required ? 'required' : 'optional';
71
+ lines.push(` - ${entry.id} (${entry.estimatedTokens.toLocaleString()} tokens, ${load}, ${entry.path})`);
72
+ }
73
+ return `${lines.join('\n')}\n`;
74
+ }
75
+ //# sourceMappingURL=context-audit.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"context-audit.js","sourceRoot":"","sources":["../src/context-audit.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,18 @@
1
+ import { type ManifestEntry } from './manifest.js';
2
+ import { type Tool } from './targets.js';
3
+ export type InstallStatus = 'installed' | 'skipped-identical' | 'skipped-conflict';
4
+ export interface InstallResult {
5
+ status: InstallStatus;
6
+ path: string;
7
+ }
8
+ export interface InstallOptions {
9
+ cwd: string;
10
+ tool: Tool;
11
+ force?: boolean;
12
+ }
13
+ export declare function installEntry(entry: ManifestEntry, opts: InstallOptions): InstallResult;
14
+ export declare function isEntryInstalled(entry: ManifestEntry, opts: {
15
+ tool: Tool;
16
+ cwd: string;
17
+ }): boolean;
18
+ //# sourceMappingURL=install.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"install.d.ts","sourceRoot":"","sources":["../src/install.ts"],"names":[],"mappings":"AAEA,OAAO,EAAe,KAAK,aAAa,EAAE,MAAM,eAAe,CAAC;AAChE,OAAO,EAAW,KAAK,IAAI,EAAE,MAAM,cAAc,CAAC;AAElD,MAAM,MAAM,aAAa,GAAG,WAAW,GAAG,mBAAmB,GAAG,kBAAkB,CAAC;AAEnF,MAAM,WAAW,aAAa;IAC5B,MAAM,EAAE,aAAa,CAAC;IACtB,IAAI,EAAE,MAAM,CAAC;CACd;AAED,MAAM,WAAW,cAAc;IAC7B,GAAG,EAAE,MAAM,CAAC;IACZ,IAAI,EAAE,IAAI,CAAC;IACX,KAAK,CAAC,EAAE,OAAO,CAAC;CACjB;AAED,wBAAgB,YAAY,CAAC,KAAK,EAAE,aAAa,EAAE,IAAI,EAAE,cAAc,GAAG,aAAa,CAqBtF;AAED,wBAAgB,gBAAgB,CAAC,KAAK,EAAE,aAAa,EAAE,IAAI,EAAE;IAAE,IAAI,EAAE,IAAI,CAAC;IAAC,GAAG,EAAE,MAAM,CAAA;CAAE,GAAG,OAAO,CAEjG"}
@@ -0,0 +1,28 @@
1
+ import { existsSync, mkdirSync, readFileSync, writeFileSync } from 'node:fs';
2
+ import { dirname, join } from 'node:path';
3
+ import { packageRoot } from './manifest.js';
4
+ import { TARGETS } from './targets.js';
5
+ export function installEntry(entry, opts) {
6
+ const sourcePath = join(packageRoot, entry.path);
7
+ if (!existsSync(sourcePath)) {
8
+ throw new Error(`Source file not found: ${sourcePath}`);
9
+ }
10
+ const sourceContent = readFileSync(sourcePath, 'utf8');
11
+ const targetPath = TARGETS[opts.tool].resolvePath(entry, opts.cwd);
12
+ if (existsSync(targetPath)) {
13
+ const existing = readFileSync(targetPath, 'utf8');
14
+ if (existing === sourceContent) {
15
+ return { status: 'skipped-identical', path: targetPath };
16
+ }
17
+ if (!opts.force) {
18
+ return { status: 'skipped-conflict', path: targetPath };
19
+ }
20
+ }
21
+ mkdirSync(dirname(targetPath), { recursive: true });
22
+ writeFileSync(targetPath, sourceContent);
23
+ return { status: 'installed', path: targetPath };
24
+ }
25
+ export function isEntryInstalled(entry, opts) {
26
+ return existsSync(TARGETS[opts.tool].resolvePath(entry, opts.cwd));
27
+ }
28
+ //# sourceMappingURL=install.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"install.js","sourceRoot":"","sources":["../src/install.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,SAAS,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,SAAS,CAAC;AAC7E,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AAC1C,OAAO,EAAE,WAAW,EAAsB,MAAM,eAAe,CAAC;AAChE,OAAO,EAAE,OAAO,EAAa,MAAM,cAAc,CAAC;AAelD,MAAM,UAAU,YAAY,CAAC,KAAoB,EAAE,IAAoB;IACrE,MAAM,UAAU,GAAG,IAAI,CAAC,WAAW,EAAE,KAAK,CAAC,IAAI,CAAC,CAAC;IACjD,IAAI,CAAC,UAAU,CAAC,UAAU,CAAC,EAAE,CAAC;QAC5B,MAAM,IAAI,KAAK,CAAC,0BAA0B,UAAU,EAAE,CAAC,CAAC;IAC1D,CAAC;IACD,MAAM,aAAa,GAAG,YAAY,CAAC,UAAU,EAAE,MAAM,CAAC,CAAC;IACvD,MAAM,UAAU,GAAG,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,WAAW,CAAC,KAAK,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC;IAEnE,IAAI,UAAU,CAAC,UAAU,CAAC,EAAE,CAAC;QAC3B,MAAM,QAAQ,GAAG,YAAY,CAAC,UAAU,EAAE,MAAM,CAAC,CAAC;QAClD,IAAI,QAAQ,KAAK,aAAa,EAAE,CAAC;YAC/B,OAAO,EAAE,MAAM,EAAE,mBAAmB,EAAE,IAAI,EAAE,UAAU,EAAE,CAAC;QAC3D,CAAC;QACD,IAAI,CAAC,IAAI,CAAC,KAAK,EAAE,CAAC;YAChB,OAAO,EAAE,MAAM,EAAE,kBAAkB,EAAE,IAAI,EAAE,UAAU,EAAE,CAAC;QAC1D,CAAC;IACH,CAAC;IAED,SAAS,CAAC,OAAO,CAAC,UAAU,CAAC,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IACpD,aAAa,CAAC,UAAU,EAAE,aAAa,CAAC,CAAC;IACzC,OAAO,EAAE,MAAM,EAAE,WAAW,EAAE,IAAI,EAAE,UAAU,EAAE,CAAC;AACnD,CAAC;AAED,MAAM,UAAU,gBAAgB,CAAC,KAAoB,EAAE,IAAiC;IACtF,OAAO,UAAU,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,WAAW,CAAC,KAAK,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC;AACrE,CAAC"}
@@ -0,0 +1,25 @@
1
+ export interface ManifestEntry {
2
+ id: string;
3
+ type: 'directive' | 'skill';
4
+ path: string;
5
+ description: string;
6
+ version: string;
7
+ required: boolean;
8
+ category: string;
9
+ tools: string[];
10
+ }
11
+ export interface Manifest {
12
+ version: string;
13
+ entries: ManifestEntry[];
14
+ }
15
+ export interface FilterOptions {
16
+ category?: string;
17
+ required?: boolean;
18
+ tool?: string;
19
+ type?: 'directive' | 'skill';
20
+ }
21
+ export declare const packageRoot: string;
22
+ export declare function loadManifest(): Manifest;
23
+ export declare function filterEntries(entries: ManifestEntry[], opts: FilterOptions): ManifestEntry[];
24
+ export declare function findEntry(entries: ManifestEntry[], id: string): ManifestEntry | undefined;
25
+ //# sourceMappingURL=manifest.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"manifest.d.ts","sourceRoot":"","sources":["../src/manifest.ts"],"names":[],"mappings":"AAIA,MAAM,WAAW,aAAa;IAC5B,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,WAAW,GAAG,OAAO,CAAC;IAC5B,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;IACpB,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,OAAO,CAAC;IAClB,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,EAAE,MAAM,EAAE,CAAC;CACjB;AAED,MAAM,WAAW,QAAQ;IACvB,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,aAAa,EAAE,CAAC;CAC1B;AAED,MAAM,WAAW,aAAa;IAC5B,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,WAAW,GAAG,OAAO,CAAC;CAC9B;AAGD,eAAO,MAAM,WAAW,QAAwB,CAAC;AAEjD,wBAAgB,YAAY,IAAI,QAAQ,CAMvC;AAED,wBAAgB,aAAa,CAAC,OAAO,EAAE,aAAa,EAAE,EAAE,IAAI,EAAE,aAAa,GAAG,aAAa,EAAE,CAQ5F;AAED,wBAAgB,SAAS,CAAC,OAAO,EAAE,aAAa,EAAE,EAAE,EAAE,EAAE,MAAM,GAAG,aAAa,GAAG,SAAS,CAEzF"}
@@ -0,0 +1,29 @@
1
+ import { existsSync, readFileSync } from 'node:fs';
2
+ import { dirname, join } from 'node:path';
3
+ import { fileURLToPath } from 'node:url';
4
+ const moduleDir = dirname(fileURLToPath(import.meta.url));
5
+ export const packageRoot = join(moduleDir, '..');
6
+ export function loadManifest() {
7
+ const manifestPath = join(packageRoot, 'manifest.json');
8
+ if (!existsSync(manifestPath)) {
9
+ throw new Error(`manifest.json not found at ${manifestPath}. Run 'npm run manifest' to generate it.`);
10
+ }
11
+ return JSON.parse(readFileSync(manifestPath, 'utf8'));
12
+ }
13
+ export function filterEntries(entries, opts) {
14
+ return entries.filter((entry) => {
15
+ if (opts.category && entry.category !== opts.category)
16
+ return false;
17
+ if (opts.required !== undefined && entry.required !== opts.required)
18
+ return false;
19
+ if (opts.tool && !entry.tools.includes(opts.tool))
20
+ return false;
21
+ if (opts.type && entry.type !== opts.type)
22
+ return false;
23
+ return true;
24
+ });
25
+ }
26
+ export function findEntry(entries, id) {
27
+ return entries.find((entry) => entry.id === id);
28
+ }
29
+ //# sourceMappingURL=manifest.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"manifest.js","sourceRoot":"","sources":["../src/manifest.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,YAAY,EAAE,MAAM,SAAS,CAAC;AACnD,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AAC1C,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAyBzC,MAAM,SAAS,GAAG,OAAO,CAAC,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC;AAC1D,MAAM,CAAC,MAAM,WAAW,GAAG,IAAI,CAAC,SAAS,EAAE,IAAI,CAAC,CAAC;AAEjD,MAAM,UAAU,YAAY;IAC1B,MAAM,YAAY,GAAG,IAAI,CAAC,WAAW,EAAE,eAAe,CAAC,CAAC;IACxD,IAAI,CAAC,UAAU,CAAC,YAAY,CAAC,EAAE,CAAC;QAC9B,MAAM,IAAI,KAAK,CAAC,8BAA8B,YAAY,0CAA0C,CAAC,CAAC;IACxG,CAAC;IACD,OAAO,IAAI,CAAC,KAAK,CAAC,YAAY,CAAC,YAAY,EAAE,MAAM,CAAC,CAAa,CAAC;AACpE,CAAC;AAED,MAAM,UAAU,aAAa,CAAC,OAAwB,EAAE,IAAmB;IACzE,OAAO,OAAO,CAAC,MAAM,CAAC,CAAC,KAAK,EAAE,EAAE;QAC9B,IAAI,IAAI,CAAC,QAAQ,IAAI,KAAK,CAAC,QAAQ,KAAK,IAAI,CAAC,QAAQ;YAAE,OAAO,KAAK,CAAC;QACpE,IAAI,IAAI,CAAC,QAAQ,KAAK,SAAS,IAAI,KAAK,CAAC,QAAQ,KAAK,IAAI,CAAC,QAAQ;YAAE,OAAO,KAAK,CAAC;QAClF,IAAI,IAAI,CAAC,IAAI,IAAI,CAAC,KAAK,CAAC,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAI,CAAC;YAAE,OAAO,KAAK,CAAC;QAChE,IAAI,IAAI,CAAC,IAAI,IAAI,KAAK,CAAC,IAAI,KAAK,IAAI,CAAC,IAAI;YAAE,OAAO,KAAK,CAAC;QACxD,OAAO,IAAI,CAAC;IACd,CAAC,CAAC,CAAC;AACL,CAAC;AAED,MAAM,UAAU,SAAS,CAAC,OAAwB,EAAE,EAAU;IAC5D,OAAO,OAAO,CAAC,IAAI,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,KAAK,CAAC,EAAE,KAAK,EAAE,CAAC,CAAC;AAClD,CAAC"}
@@ -0,0 +1,3 @@
1
+ export declare function ask(question: string): Promise<string>;
2
+ export declare function selectMultiple(question: string, options: string[]): Promise<string[]>;
3
+ //# sourceMappingURL=prompt.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"prompt.d.ts","sourceRoot":"","sources":["../src/prompt.ts"],"names":[],"mappings":"AAKA,wBAAsB,GAAG,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,CAO3D;AAED,wBAAsB,cAAc,CAAC,QAAQ,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,CAY3F"}
package/dist/prompt.js ADDED
@@ -0,0 +1,29 @@
1
+ import { stdin, stdout } from 'node:process';
2
+ import { createInterface } from 'node:readline/promises';
3
+ const DECIMAL_RADIX = 10;
4
+ export async function ask(question) {
5
+ const rl = createInterface({ input: stdin, output: stdout });
6
+ try {
7
+ return (await rl.question(question)).trim();
8
+ }
9
+ finally {
10
+ rl.close();
11
+ }
12
+ }
13
+ export async function selectMultiple(question, options) {
14
+ if (options.length === 0)
15
+ return [];
16
+ stdout.write(`${question}\n`);
17
+ options.forEach((opt, i) => stdout.write(` ${i + 1}) ${opt}\n`));
18
+ const answer = (await ask('Select numbers separated by space (or "all", "none"): ')).toLowerCase();
19
+ if (answer === 'all')
20
+ return [...options];
21
+ if (answer === '' || answer === 'none')
22
+ return [];
23
+ const indices = answer
24
+ .split(/\s+/)
25
+ .map((token) => Number.parseInt(token, DECIMAL_RADIX) - 1)
26
+ .filter((index) => Number.isInteger(index) && index >= 0 && index < options.length);
27
+ return [...new Set(indices)].map((index) => options[index]);
28
+ }
29
+ //# sourceMappingURL=prompt.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"prompt.js","sourceRoot":"","sources":["../src/prompt.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,cAAc,CAAC;AAC7C,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AAEzD,MAAM,aAAa,GAAG,EAAE,CAAC;AAEzB,MAAM,CAAC,KAAK,UAAU,GAAG,CAAC,QAAgB;IACxC,MAAM,EAAE,GAAG,eAAe,CAAC,EAAE,KAAK,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC;IAC7D,IAAI,CAAC;QACH,OAAO,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC;IAC9C,CAAC;YAAS,CAAC;QACT,EAAE,CAAC,KAAK,EAAE,CAAC;IACb,CAAC;AACH,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,cAAc,CAAC,QAAgB,EAAE,OAAiB;IACtE,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,EAAE,CAAC;IACpC,MAAM,CAAC,KAAK,CAAC,GAAG,QAAQ,IAAI,CAAC,CAAC;IAC9B,OAAO,CAAC,OAAO,CAAC,CAAC,GAAG,EAAE,CAAC,EAAE,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,KAAK,GAAG,IAAI,CAAC,CAAC,CAAC;IAClE,MAAM,MAAM,GAAG,CAAC,MAAM,GAAG,CAAC,wDAAwD,CAAC,CAAC,CAAC,WAAW,EAAE,CAAC;IACnG,IAAI,MAAM,KAAK,KAAK;QAAE,OAAO,CAAC,GAAG,OAAO,CAAC,CAAC;IAC1C,IAAI,MAAM,KAAK,EAAE,IAAI,MAAM,KAAK,MAAM;QAAE,OAAO,EAAE,CAAC;IAClD,MAAM,OAAO,GAAG,MAAM;SACnB,KAAK,CAAC,KAAK,CAAC;SACZ,GAAG,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,MAAM,CAAC,QAAQ,CAAC,KAAK,EAAE,aAAa,CAAC,GAAG,CAAC,CAAC;SACzD,MAAM,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,MAAM,CAAC,SAAS,CAAC,KAAK,CAAC,IAAI,KAAK,IAAI,CAAC,IAAI,KAAK,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IACtF,OAAO,CAAC,GAAG,IAAI,GAAG,CAAC,OAAO,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,CAAC;AAC9D,CAAC"}
@@ -0,0 +1,10 @@
1
+ import type { ManifestEntry } from './manifest.js';
2
+ export type Tool = 'claude' | 'copilot' | 'codex' | 'cursor';
3
+ export declare const KNOWN_TOOLS: readonly Tool[];
4
+ export declare function isTool(value: string): value is Tool;
5
+ export interface TargetConfig {
6
+ resolvePath: (entry: ManifestEntry, cwd: string) => string;
7
+ }
8
+ export declare const TARGETS: Record<Tool, TargetConfig>;
9
+ export declare function detectTool(cwd: string): Tool | null;
10
+ //# sourceMappingURL=targets.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"targets.d.ts","sourceRoot":"","sources":["../src/targets.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,eAAe,CAAC;AAEnD,MAAM,MAAM,IAAI,GAAG,QAAQ,GAAG,SAAS,GAAG,OAAO,GAAG,QAAQ,CAAC;AAE7D,eAAO,MAAM,WAAW,EAAE,SAAS,IAAI,EAA6C,CAAC;AAErF,wBAAgB,MAAM,CAAC,KAAK,EAAE,MAAM,GAAG,KAAK,IAAI,IAAI,CAEnD;AAED,MAAM,WAAW,YAAY;IAC3B,WAAW,EAAE,CAAC,KAAK,EAAE,aAAa,EAAE,GAAG,EAAE,MAAM,KAAK,MAAM,CAAC;CAC5D;AAED,eAAO,MAAM,OAAO,EAAE,MAAM,CAAC,IAAI,EAAE,YAAY,CAa9C,CAAC;AAEF,wBAAgB,UAAU,CAAC,GAAG,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI,CAMnD"}
@@ -0,0 +1,32 @@
1
+ import { existsSync } from 'node:fs';
2
+ import { join } from 'node:path';
3
+ export const KNOWN_TOOLS = ['claude', 'copilot', 'codex', 'cursor'];
4
+ export function isTool(value) {
5
+ return KNOWN_TOOLS.includes(value);
6
+ }
7
+ export const TARGETS = {
8
+ claude: {
9
+ resolvePath: (entry, cwd) => join(cwd, entry.path),
10
+ },
11
+ copilot: {
12
+ resolvePath: (entry, cwd) => join(cwd, entry.path),
13
+ },
14
+ codex: {
15
+ resolvePath: (entry, cwd) => join(cwd, entry.path),
16
+ },
17
+ cursor: {
18
+ resolvePath: (entry, cwd) => join(cwd, '.cursor', 'rules', `${entry.id}.mdc`),
19
+ },
20
+ };
21
+ export function detectTool(cwd) {
22
+ if (existsSync(join(cwd, '.cursor')))
23
+ return 'cursor';
24
+ if (existsSync(join(cwd, '.github', 'copilot-instructions.md')))
25
+ return 'copilot';
26
+ if (existsSync(join(cwd, 'AGENTS.md')))
27
+ return 'codex';
28
+ if (existsSync(join(cwd, 'CLAUDE.md')) || existsSync(join(cwd, '.claude')))
29
+ return 'claude';
30
+ return null;
31
+ }
32
+ //# sourceMappingURL=targets.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"targets.js","sourceRoot":"","sources":["../src/targets.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AACrC,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AAKjC,MAAM,CAAC,MAAM,WAAW,GAAoB,CAAC,QAAQ,EAAE,SAAS,EAAE,OAAO,EAAE,QAAQ,CAAC,CAAC;AAErF,MAAM,UAAU,MAAM,CAAC,KAAa;IAClC,OAAQ,WAAiC,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC;AAC5D,CAAC;AAMD,MAAM,CAAC,MAAM,OAAO,GAA+B;IACjD,MAAM,EAAE;QACN,WAAW,EAAE,CAAC,KAAK,EAAE,GAAG,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,CAAC;KACnD;IACD,OAAO,EAAE;QACP,WAAW,EAAE,CAAC,KAAK,EAAE,GAAG,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,CAAC;KACnD;IACD,KAAK,EAAE;QACL,WAAW,EAAE,CAAC,KAAK,EAAE,GAAG,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,CAAC;KACnD;IACD,MAAM,EAAE;QACN,WAAW,EAAE,CAAC,KAAK,EAAE,GAAG,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE,SAAS,EAAE,OAAO,EAAE,GAAG,KAAK,CAAC,EAAE,MAAM,CAAC;KAC9E;CACF,CAAC;AAEF,MAAM,UAAU,UAAU,CAAC,GAAW;IACpC,IAAI,UAAU,CAAC,IAAI,CAAC,GAAG,EAAE,SAAS,CAAC,CAAC;QAAE,OAAO,QAAQ,CAAC;IACtD,IAAI,UAAU,CAAC,IAAI,CAAC,GAAG,EAAE,SAAS,EAAE,yBAAyB,CAAC,CAAC;QAAE,OAAO,SAAS,CAAC;IAClF,IAAI,UAAU,CAAC,IAAI,CAAC,GAAG,EAAE,WAAW,CAAC,CAAC;QAAE,OAAO,OAAO,CAAC;IACvD,IAAI,UAAU,CAAC,IAAI,CAAC,GAAG,EAAE,WAAW,CAAC,CAAC,IAAI,UAAU,CAAC,IAAI,CAAC,GAAG,EAAE,SAAS,CAAC,CAAC;QAAE,OAAO,QAAQ,CAAC;IAC5F,OAAO,IAAI,CAAC;AACd,CAAC"}