reyson-spec-gate 0.1.0 → 0.1.1

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/README.md CHANGED
@@ -1,272 +1,254 @@
1
- # skill-reyson
1
+ # reyson-spec-gate
2
2
 
3
- An interactive npm installer for a spec-first coding workflow.
3
+ A spec-first installer for coding-agent workflow rules, docs, and skills.
4
4
 
5
- `skill-reyson` helps teams install a lightweight scaffold that makes coding agents slower in the right place: **before implementation starts**.
5
+ `reyson-spec-gate` is designed to install a consistent pre-coding workflow into a workspace so that agents do not jump directly from a loose request into implementation.
6
6
 
7
- It enforces a simple rule:
7
+ Its central rule is simple:
8
8
 
9
9
  > No coding before the spec is clear, the task list exists, and the checklist exists.
10
10
 
11
11
  ---
12
12
 
13
- ## What this package installs
13
+ ## Recommended usage
14
14
 
15
- By default, the installer copies only the core workflow assets into your target directory:
15
+ Do **not** rely on global installation as the primary path.
16
+
17
+ The recommended way to use this package is:
18
+
19
+ ```bash
20
+ npx reyson-spec-gate
21
+ ```
22
+
23
+ This launches the interactive installer directly and avoids depending on a permanently global npm installation.
24
+
25
+ ---
26
+
27
+ ## What it installs
28
+
29
+ The installer always installs the shared workflow assets:
16
30
 
17
31
  - `docs/spec-workflow.md`
18
32
  - `skills/generate-task-list/SKILL.md`
19
33
  - `skills/generate-checklist/SKILL.md`
20
34
 
21
- By default, it **does not** install agent guidance files.
35
+ It also installs **RULES.md only** for selected agents.
22
36
 
23
- If you choose to install agent guidance files during setup, it can also add one or more of:
37
+ It does **not** install:
38
+ - `AGENTS.md`
39
+ - `CLAUDE.md`
24
40
 
25
- - `AGENTS.md` for Codex-style workflows
26
- - `CLAUDE.md` for Claude Code-style workflows
27
- - `RULES.md` as a generic rules entrypoint
41
+ All agent-specific rule entrypoints are normalized to `RULES.md`.
28
42
 
29
43
  ---
30
44
 
31
- ## Installation
45
+ ## Supported agents
32
46
 
33
- ```bash
34
- npm i -g reyson-spec-gate
35
- ```
36
-
37
- ## Quick start
47
+ The interactive installer currently supports these agent targets:
38
48
 
39
- Install globally, then run the interactive installer:
49
+ 1. Codex
50
+ 2. Trae
51
+ 3. Claude Code
52
+ 4. Cursor
53
+ 5. Antigravity
40
54
 
41
- ```bash
42
- skill-reyson
43
- ```
55
+ You can select one or more targets in the same run.
44
56
 
45
- Fast path examples:
57
+ If you do not select anything, the installer will:
58
+ - default to **Codex**
59
+ - print a message explaining that Codex was chosen by default
46
60
 
47
- ```bash
48
- # install only docs + skills into the current project
49
- skill-reyson install --yes --dir .
61
+ ---
50
62
 
51
- # install docs + skills + Codex AGENTS.md
52
- skill-reyson install --yes --dir . --with-agent-files --agents codex
53
- ```
63
+ ## Interactive behavior
54
64
 
55
- Then run:
65
+ Run:
56
66
 
57
67
  ```bash
58
- skill-reyson
68
+ npx reyson-spec-gate
59
69
  ```
60
70
 
61
- or:
71
+ The installer will ask:
72
+ 1. which directory to install into
73
+ 2. which agent targets to install for
62
74
 
63
- ```bash
64
- skill-reyson install
65
- ```
66
-
67
- ---
75
+ Agent selection is multi-select.
68
76
 
69
- ## Interactive setup
77
+ Example:
78
+ - `1,3,4` installs for Codex, Claude Code, and Cursor
70
79
 
71
- The CLI is interactive by default.
80
+ If you press ENTER without choosing an agent, it falls back to Codex.
72
81
 
73
- It asks:
74
- 1. where to install the scaffold
75
- 2. whether to install agent guidance files
76
- 3. which agent adapters to install
82
+ ---
77
83
 
78
- ### Default behavior
84
+ ## Output structure
79
85
 
80
- If you accept the defaults:
81
- - docs and skills are installed
82
- - `AGENTS.md` / `CLAUDE.md` / `RULES.md` are **not** installed
86
+ The installer writes the shared assets into the target directory and installs rule files per agent under `agents/<agent>/RULES.md`.
83
87
 
84
- This matches your desired safe default: **no agent behavior file unless the user opts in**.
88
+ Example output:
85
89
 
86
- ---
90
+ ```text
91
+ my-project/
92
+ ├── docs/
93
+ │ └── spec-workflow.md
94
+ ├── skills/
95
+ │ ├── generate-task-list/
96
+ │ │ └── SKILL.md
97
+ │ └── generate-checklist/
98
+ │ └── SKILL.md
99
+ └── agents/
100
+ ├── codex/
101
+ │ └── RULES.md
102
+ ├── claude-code/
103
+ │ └── RULES.md
104
+ └── cursor/
105
+ └── RULES.md
106
+ ```
87
107
 
88
- ## Non-interactive setup
108
+ This structure avoids filename collisions when multiple agents are installed in one run.
89
109
 
90
- You can also run the installer non-interactively.
110
+ ---
91
111
 
92
- ### Install core files only
112
+ ## Non-interactive usage
93
113
 
94
- ```bash
95
- skill-reyson install --yes --dir ./my-project
96
- ```
114
+ If you want a scriptable path, you can still run the installer non-interactively.
97
115
 
98
- ### Install core files plus Codex adapter
116
+ ### Default to Codex
99
117
 
100
118
  ```bash
101
- skill-reyson install --yes --dir ./my-project --with-agent-files --agents codex
119
+ npx reyson-spec-gate install --yes --dir ./my-project
102
120
  ```
103
121
 
104
- ### Install multiple agent adapters
122
+ ### Install multiple agent targets
105
123
 
106
124
  ```bash
107
- skill-reyson install --yes --dir ./my-project --with-agent-files --agents codex,claude,generic
125
+ npx reyson-spec-gate install --yes --dir ./my-project --agents codex,trae,claude,cursor,antigravity
108
126
  ```
109
127
 
110
128
  ---
111
129
 
112
- ## Why this exists
113
-
114
- In many spec-driven workflows, an agent may produce a decent spec and still move into coding too early.
130
+ ## Why `npx` is preferred
115
131
 
116
- Typical failure modes:
117
- - the task list is implicit instead of explicit
118
- - the checklist is missing or too generic
119
- - the agent starts coding before execution and verification artifacts are aligned
132
+ The purpose of this package is to run an installation workflow, not simply to sit globally on a machine.
120
133
 
121
- `skill-reyson` fixes this by separating the workflow into three responsibilities:
134
+ Using `npx reyson-spec-gate` is preferable because:
135
+ - it is explicit
136
+ - it is easy to run in any repository
137
+ - it avoids stale global versions
138
+ - it keeps the install workflow lightweight
122
139
 
123
- - **agent guidance files** tell the agent how to behave
124
- - **docs** explain the workflow and readiness gate
125
- - **skills** generate missing artifacts
140
+ Global installation can still work, but it is no longer the recommended entrypoint.
126
141
 
127
142
  ---
128
143
 
129
- ## Repository structure
130
-
131
- ```text
132
- skill-reyson/
133
- ├── AGENTS.md
134
- ├── LICENSE
135
- ├── README.md
136
- ├── package.json
137
- ├── bin/
138
- │ └── skill-reyson.js
139
- ├── docs/
140
- │ └── spec-workflow.md
141
- ├── examples/
142
- │ ├── example-derived-artifacts.md
143
- │ └── example-input-spec.md
144
- ├── skills/
145
- │ ├── generate-task-list/
146
- │ │ └── SKILL.md
147
- │ └── generate-checklist/
148
- │ └── SKILL.md
149
- └── templates/
150
- └── adapters/
151
- ├── AGENTS.md
152
- ├── CLAUDE.md
153
- └── RULES.md
154
- ```
144
+ ## Workflow model
155
145
 
156
- ---
146
+ This package is based on a spec-first coding workflow.
157
147
 
158
- ## Responsibility split
148
+ The intended flow is:
159
149
 
160
- ### 1. Agent guidance files
150
+ 1. The agent reads `docs/spec-workflow.md`
151
+ 2. The agent checks whether the current work has:
152
+ - a working spec
153
+ - a task list
154
+ - a checklist
155
+ 3. If the task list is missing, the agent uses `generate-task-list`
156
+ 4. If the checklist is missing, the agent uses `generate-checklist`
157
+ 5. Only after both artifacts exist does coding begin
158
+ 6. After coding, the checklist is revisited before claiming completion
161
159
 
162
- Optional files such as `AGENTS.md`, `CLAUDE.md`, or `RULES.md` act as the enforcement layer.
160
+ ---
163
161
 
164
- Their job is to tell the agent:
165
- - read the workflow doc before coding
166
- - check whether task list and checklist exist
167
- - generate missing artifacts before implementation
168
- - revisit the checklist after coding
162
+ ## Responsibilities
169
163
 
170
- ### 2. `docs/spec-workflow.md`
164
+ ### `docs/spec-workflow.md`
171
165
 
172
- This is the workflow knowledge layer.
166
+ This file is the workflow knowledge source.
173
167
 
174
168
  It defines:
175
169
  - the pre-coding gate
176
- - artifact ordering rules
177
- - task-list expectations
178
- - checklist expectations
170
+ - artifact ordering
171
+ - task-list requirements
172
+ - checklist requirements
179
173
  - coding readiness rules
180
- - post-coding review rules
174
+ - post-coding verification rules
181
175
 
182
- ### 3. Skills
176
+ ### `skills/generate-task-list`
183
177
 
184
- The two included skills are execution helpers.
178
+ This skill generates or normalizes an explicit task list from a spec or plan.
185
179
 
186
- #### `generate-task-list`
187
- Use this when the workflow has a spec or plan but no explicit task list.
180
+ ### `skills/generate-checklist`
188
181
 
189
- #### `generate-checklist`
190
- Use this when the workflow has a spec and task list but no explicit checklist.
182
+ This skill generates a checklist from the working spec and task list.
191
183
 
192
- ---
184
+ ### `agents/<agent>/RULES.md`
193
185
 
194
- ## Core workflow
186
+ Each selected agent receives a `RULES.md` entrypoint.
195
187
 
196
- 1. Read the workflow document
197
- 2. Check whether the current task has a working spec
198
- 3. Check whether a task list exists
199
- 4. Check whether a checklist exists
200
- 5. If task list is missing, generate it
201
- 6. If checklist is missing, generate it
202
- 7. Start coding only after the readiness gate is satisfied
203
- 8. Revisit the checklist after coding
188
+ Its job is to remind the target agent to:
189
+ - read the workflow doc first
190
+ - check for task list and checklist presence
191
+ - generate missing artifacts before implementation
192
+ - avoid coding before the pre-coding gate passes
204
193
 
205
194
  ---
206
195
 
207
- ## Included examples
196
+ ## Example installation commands
208
197
 
209
- See:
210
- - `examples/example-input-spec.md`
211
- - `examples/example-derived-artifacts.md`
198
+ ### Install for Codex only
212
199
 
213
- These show how a spec can lead to an explicit task list and checklist before coding begins.
200
+ ```bash
201
+ npx reyson-spec-gate install --yes --dir ./my-project --agents codex
202
+ ```
214
203
 
215
- ---
204
+ ### Install for Trae and Cursor
216
205
 
217
- ## Development
206
+ ```bash
207
+ npx reyson-spec-gate install --yes --dir ./my-project --agents trae,cursor
208
+ ```
218
209
 
219
- Run locally without publishing:
210
+ ### Install for all supported agents
220
211
 
221
212
  ```bash
222
- node bin/skill-reyson.js --help
223
- node bin/skill-reyson.js install
213
+ npx reyson-spec-gate install --yes --dir ./my-project --agents codex,trae,claude,cursor,antigravity
224
214
  ```
225
215
 
226
216
  ---
227
217
 
228
- ## Open-source intent
218
+ ## Development
229
219
 
230
- This project is meant to stay small, composable, and easy to adapt.
220
+ Run locally:
231
221
 
232
- Good future extensions:
233
- - additional agent adapters
234
- - a readiness report skill
235
- - templates for Working Spec output
236
- - project-specific workflow variants
237
- - validation fixtures and smoke tests
222
+ ```bash
223
+ node bin/reyson-spec-gate.js --help
224
+ node bin/reyson-spec-gate.js install
225
+ ```
238
226
 
239
227
  ---
240
228
 
241
- ## Publish checklist
229
+ ## Package identity
242
230
 
243
- Before publishing to GitHub or npm, verify:
244
-
245
- - `node bin/skill-reyson.js --help` works
246
- - `skill-reyson install --yes --dir /tmp/somewhere` copies the expected files
247
- - default install does **not** copy agent guidance files
248
- - `--with-agent-files --agents ...` copies the selected adapter files
249
- - `README.md` matches current CLI behavior
250
- - `package.json` name, version, license, and bin entry are correct
251
-
252
- ### Suggested GitHub steps
231
+ Current npm package:
253
232
 
254
233
  ```bash
255
- cd /Users/bytedance/Desktop/coding/skill-reyson
256
- git remote add origin <your-github-repo-url>
257
- git push -u origin master
234
+ reyson-spec-gate
258
235
  ```
259
236
 
260
- ### Suggested npm publish steps
237
+ Recommended invocation:
261
238
 
262
239
  ```bash
263
- cd /Users/bytedance/Desktop/coding/skill-reyson
264
- npm login
265
- npm publish
240
+ npx reyson-spec-gate
266
241
  ```
267
242
 
268
- If you want a safer dry run first:
243
+ ---
269
244
 
270
- ```bash
271
- npm pack
272
- ```
245
+ ## Notes
246
+
247
+ This repository intentionally standardizes every agent rule entrypoint to `RULES.md`.
248
+
249
+ That means:
250
+ - no `AGENTS.md`
251
+ - no `CLAUDE.md`
252
+ - a single normalized rules filename for all supported agent targets
253
+
254
+ This keeps the workflow easier to reason about and easier to extend.
@@ -0,0 +1,239 @@
1
+ #!/usr/bin/env node
2
+ const fs = require('fs');
3
+ const path = require('path');
4
+ const readline = require('readline');
5
+
6
+ const PACKAGE_ROOT = path.resolve(__dirname, '..');
7
+ const DOC_SOURCE = path.join(PACKAGE_ROOT, 'docs', 'spec-workflow.md');
8
+ const RULES_SOURCE = path.join(PACKAGE_ROOT, 'templates', 'RULES.md');
9
+ const SKILL_SOURCES = [
10
+ {
11
+ source: path.join(PACKAGE_ROOT, 'skills', 'generate-task-list', 'SKILL.md'),
12
+ relativeTarget: path.join('skills', 'generate-task-list', 'SKILL.md'),
13
+ },
14
+ {
15
+ source: path.join(PACKAGE_ROOT, 'skills', 'generate-checklist', 'SKILL.md'),
16
+ relativeTarget: path.join('skills', 'generate-checklist', 'SKILL.md'),
17
+ },
18
+ ];
19
+
20
+ const AGENTS = {
21
+ codex: { label: 'Codex', target: path.join('agents', 'codex', 'RULES.md') },
22
+ trae: { label: 'Trae', target: path.join('agents', 'trae', 'RULES.md') },
23
+ claude: { label: 'Claude Code', target: path.join('agents', 'claude-code', 'RULES.md') },
24
+ cursor: { label: 'Cursor', target: path.join('agents', 'cursor', 'RULES.md') },
25
+ antigravity: { label: 'Antigravity', target: path.join('agents', 'antigravity', 'RULES.md') },
26
+ };
27
+ const DEFAULT_AGENT = 'codex';
28
+ const AGENT_NUMBER_MAP = { '1': 'codex', '2': 'trae', '3': 'claude', '4': 'cursor', '5': 'antigravity' };
29
+
30
+ function printHelp() {
31
+ console.log(`reyson-spec-gate
32
+
33
+ Recommended usage:
34
+ npx reyson-spec-gate
35
+
36
+ Other usage:
37
+ reyson-spec-gate Start interactive installer
38
+ reyson-spec-gate install Start interactive installer
39
+ reyson-spec-gate install --dir <path>
40
+ reyson-spec-gate install --yes [--dir <path>] [--agents codex,trae,claude,cursor,antigravity]
41
+ reyson-spec-gate --help Show help
42
+
43
+ Interactive defaults:
44
+ - Installs docs/spec-workflow.md
45
+ - Installs skills/generate-task-list/SKILL.md
46
+ - Installs skills/generate-checklist/SKILL.md
47
+ - Prompts for agent selection
48
+ - If no agent is selected, defaults to Codex
49
+ - Installs RULES.md only (never AGENTS.md / CLAUDE.md)
50
+ `);
51
+ }
52
+
53
+ function parseArgs(argv) {
54
+ const args = argv.slice(2);
55
+ const options = { command: 'install', dir: process.cwd(), yes: false, agents: [] };
56
+ if (args[0] && !args[0].startsWith('-')) {
57
+ options.command = args.shift();
58
+ }
59
+ for (let i = 0; i < args.length; i += 1) {
60
+ const arg = args[i];
61
+ if (arg === '--help' || arg === '-h') {
62
+ options.command = 'help';
63
+ } else if (arg === '--yes' || arg === '-y') {
64
+ options.yes = true;
65
+ } else if (arg === '--dir') {
66
+ options.dir = path.resolve(args[i + 1] || process.cwd());
67
+ i += 1;
68
+ } else if (arg.startsWith('--dir=')) {
69
+ options.dir = path.resolve(arg.split('=')[1]);
70
+ } else if (arg === '--agents') {
71
+ options.agents = (args[i + 1] || '').split(',').map((s) => s.trim()).filter(Boolean);
72
+ i += 1;
73
+ } else if (arg.startsWith('--agents=')) {
74
+ options.agents = arg.split('=')[1].split(',').map((s) => s.trim()).filter(Boolean);
75
+ } else {
76
+ throw new Error(`Unknown argument: ${arg}`);
77
+ }
78
+ }
79
+ return options;
80
+ }
81
+
82
+ function ensureDir(dirPath) {
83
+ fs.mkdirSync(dirPath, { recursive: true });
84
+ }
85
+
86
+ function copyFile(source, target) {
87
+ ensureDir(path.dirname(target));
88
+ fs.copyFileSync(source, target);
89
+ }
90
+
91
+ function normalizeAgents(agentKeys) {
92
+ return Array.from(new Set(agentKeys.map((key) => key.toLowerCase()).filter((key) => AGENTS[key])));
93
+ }
94
+
95
+ function copyCoreArtifacts(targetDir) {
96
+ const docTarget = path.join(targetDir, 'docs', 'spec-workflow.md');
97
+ copyFile(DOC_SOURCE, docTarget);
98
+ for (const skill of SKILL_SOURCES) {
99
+ copyFile(skill.source, path.join(targetDir, skill.relativeTarget));
100
+ }
101
+ return [
102
+ path.relative(targetDir, docTarget),
103
+ ...SKILL_SOURCES.map((skill) => skill.relativeTarget),
104
+ ];
105
+ }
106
+
107
+ function copyRulesFiles(targetDir, selectedAgents) {
108
+ const copied = [];
109
+ for (const key of selectedAgents) {
110
+ const agent = AGENTS[key];
111
+ if (!agent) continue;
112
+ copyFile(RULES_SOURCE, path.join(targetDir, agent.target));
113
+ copied.push(agent.target);
114
+ }
115
+ return copied;
116
+ }
117
+
118
+ function createInterface() {
119
+ return readline.createInterface({ input: process.stdin, output: process.stdout });
120
+ }
121
+
122
+ function ask(rl, question) {
123
+ return new Promise((resolve) => rl.question(question, resolve));
124
+ }
125
+
126
+ function parseInteractiveAgents(answer) {
127
+ const raw = answer.trim();
128
+ if (!raw) {
129
+ return { agents: [DEFAULT_AGENT], usedDefault: true };
130
+ }
131
+ const selected = normalizeAgents(raw.split(',').map((token) => {
132
+ const trimmed = token.trim();
133
+ return AGENT_NUMBER_MAP[trimmed] || trimmed;
134
+ }));
135
+ if (selected.length === 0) {
136
+ return { agents: [DEFAULT_AGENT], usedDefault: true };
137
+ }
138
+ return { agents: selected, usedDefault: false };
139
+ }
140
+
141
+ function performInstall({ targetDir, agents }) {
142
+ ensureDir(targetDir);
143
+ const coreFiles = copyCoreArtifacts(targetDir);
144
+ const normalizedAgents = normalizeAgents(agents);
145
+ const finalAgents = normalizedAgents.length > 0 ? normalizedAgents : [DEFAULT_AGENT];
146
+ const rulesFiles = copyRulesFiles(targetDir, finalAgents);
147
+ return { targetDir, coreFiles, rulesFiles, agents: finalAgents };
148
+ }
149
+
150
+ function printSummary(result) {
151
+ console.log('\nInstalled reyson-spec-gate scaffold:\n');
152
+ console.log(`Target: ${result.targetDir}`);
153
+ console.log('\nCore files:');
154
+ for (const file of result.coreFiles) {
155
+ console.log(` - ${file}`);
156
+ }
157
+ console.log('\nAgent rule files:');
158
+ for (const file of result.rulesFiles) {
159
+ console.log(` - ${file}`);
160
+ }
161
+ console.log(`\nSelected agents: ${result.agents.map((agent) => AGENTS[agent].label).join(', ')}`);
162
+ console.log('\nNext steps:');
163
+ console.log(' 1) Open docs/spec-workflow.md');
164
+ console.log(' 2) Point your chosen agent(s) at their installed RULES.md file(s)');
165
+ console.log(' 3) Use generate-task-list and generate-checklist when artifacts are missing');
166
+ }
167
+
168
+ async function runInteractive(defaults) {
169
+ const rl = createInterface();
170
+ try {
171
+ console.log('\nreyson-spec-gate interactive installer\n');
172
+ console.log('Recommended usage: npx reyson-spec-gate');
173
+ const dirAnswer = await ask(rl, `\nTarget directory [${defaults.dir}]: `);
174
+ const targetDir = path.resolve(dirAnswer.trim() || defaults.dir);
175
+
176
+ console.log('\nSelect agent targets (comma-separated, multi-select supported):');
177
+ console.log(' 1) Codex');
178
+ console.log(' 2) Trae');
179
+ console.log(' 3) Claude Code');
180
+ console.log(' 4) Cursor');
181
+ console.log(' 5) Antigravity');
182
+ console.log(' Press ENTER to accept the default: Codex');
183
+ const agentAnswer = await ask(rl, 'Choice(s) [Codex default]: ');
184
+ const { agents, usedDefault } = parseInteractiveAgents(agentAnswer);
185
+ if (usedDefault) {
186
+ console.log('No valid selection provided. Defaulting to Codex.');
187
+ }
188
+
189
+ const confirmation = await ask(
190
+ rl,
191
+ `\nProceed installing into ${targetDir} for ${agents.map((agent) => AGENTS[agent].label).join(', ')}? [Y/n]: `,
192
+ );
193
+ const ok = confirmation.trim() === '' || /^y(es)?$/i.test(confirmation.trim());
194
+ if (!ok) {
195
+ console.log('Installation cancelled.');
196
+ return;
197
+ }
198
+
199
+ const result = performInstall({ targetDir, agents });
200
+ printSummary(result);
201
+ } finally {
202
+ rl.close();
203
+ }
204
+ }
205
+
206
+ async function main() {
207
+ let options;
208
+ try {
209
+ options = parseArgs(process.argv);
210
+ } catch (error) {
211
+ console.error(error.message);
212
+ printHelp();
213
+ process.exit(1);
214
+ }
215
+
216
+ if (options.command === 'help' || options.command === '--help' || options.command === '-h') {
217
+ printHelp();
218
+ return;
219
+ }
220
+
221
+ if (options.command !== 'install') {
222
+ console.error(`Unknown command: ${options.command}`);
223
+ printHelp();
224
+ process.exit(1);
225
+ }
226
+
227
+ if (options.yes) {
228
+ const result = performInstall({ targetDir: options.dir, agents: options.agents });
229
+ printSummary(result);
230
+ return;
231
+ }
232
+
233
+ await runInteractive(options);
234
+ }
235
+
236
+ main().catch((error) => {
237
+ console.error(error.stack || error.message);
238
+ process.exit(1);
239
+ });
@@ -1,234 +1,2 @@
1
1
  #!/usr/bin/env node
2
- const fs = require('fs');
3
- const path = require('path');
4
- const os = require('os');
5
- const readline = require('readline');
6
-
7
- const PACKAGE_ROOT = path.resolve(__dirname, '..');
8
- const DOC_SOURCE = path.join(PACKAGE_ROOT, 'docs', 'spec-workflow.md');
9
- const SKILL_SOURCES = [
10
- {
11
- source: path.join(PACKAGE_ROOT, 'skills', 'generate-task-list', 'SKILL.md'),
12
- relativeTarget: path.join('skills', 'generate-task-list', 'SKILL.md'),
13
- },
14
- {
15
- source: path.join(PACKAGE_ROOT, 'skills', 'generate-checklist', 'SKILL.md'),
16
- relativeTarget: path.join('skills', 'generate-checklist', 'SKILL.md'),
17
- },
18
- ];
19
- const ADAPTERS = {
20
- codex: {
21
- label: 'Codex',
22
- source: path.join(PACKAGE_ROOT, 'templates', 'adapters', 'AGENTS.md'),
23
- target: 'AGENTS.md',
24
- },
25
- claude: {
26
- label: 'Claude Code',
27
- source: path.join(PACKAGE_ROOT, 'templates', 'adapters', 'CLAUDE.md'),
28
- target: 'CLAUDE.md',
29
- },
30
- generic: {
31
- label: 'Generic rules',
32
- source: path.join(PACKAGE_ROOT, 'templates', 'adapters', 'RULES.md'),
33
- target: 'RULES.md',
34
- },
35
- };
36
-
37
- function printHelp() {
38
- console.log(`skill-reyson
39
-
40
- Usage:
41
- skill-reyson Start interactive installer
42
- skill-reyson install Start interactive installer
43
- skill-reyson install --dir <path> [--agents codex,claude,generic] [--with-agent-files]
44
- skill-reyson install --yes [--dir <path>] [--agents codex,claude,generic] [--with-agent-files]
45
- skill-reyson --help Show help
46
-
47
- Defaults:
48
- - Installs docs/spec-workflow.md
49
- - Installs skills/generate-task-list/SKILL.md
50
- - Installs skills/generate-checklist/SKILL.md
51
- - Does NOT install agent guidance files unless requested
52
- `);
53
- }
54
-
55
- function parseArgs(argv) {
56
- const args = argv.slice(2);
57
- const options = { command: 'install', dir: process.cwd(), yes: false, withAgentFiles: false, agents: [] };
58
- if (args[0] && !args[0].startsWith('-')) {
59
- options.command = args.shift();
60
- }
61
- for (let i = 0; i < args.length; i += 1) {
62
- const arg = args[i];
63
- if (arg === '--help' || arg === '-h') {
64
- options.command = 'help';
65
- } else if (arg === '--yes' || arg === '-y') {
66
- options.yes = true;
67
- } else if (arg === '--with-agent-files') {
68
- options.withAgentFiles = true;
69
- } else if (arg === '--dir') {
70
- options.dir = path.resolve(args[i + 1] || process.cwd());
71
- i += 1;
72
- } else if (arg.startsWith('--dir=')) {
73
- options.dir = path.resolve(arg.split('=')[1]);
74
- } else if (arg === '--agents') {
75
- options.agents = (args[i + 1] || '').split(',').map((s) => s.trim()).filter(Boolean);
76
- i += 1;
77
- } else if (arg.startsWith('--agents=')) {
78
- options.agents = arg.split('=')[1].split(',').map((s) => s.trim()).filter(Boolean);
79
- } else {
80
- throw new Error(`Unknown argument: ${arg}`);
81
- }
82
- }
83
- return options;
84
- }
85
-
86
- function ensureDir(dirPath) {
87
- fs.mkdirSync(dirPath, { recursive: true });
88
- }
89
-
90
- function copyFile(source, target) {
91
- ensureDir(path.dirname(target));
92
- fs.copyFileSync(source, target);
93
- }
94
-
95
- function copyCoreArtifacts(targetDir) {
96
- const docTarget = path.join(targetDir, 'docs', 'spec-workflow.md');
97
- copyFile(DOC_SOURCE, docTarget);
98
- for (const skill of SKILL_SOURCES) {
99
- copyFile(skill.source, path.join(targetDir, skill.relativeTarget));
100
- }
101
- return [
102
- path.relative(targetDir, docTarget),
103
- ...SKILL_SOURCES.map((skill) => skill.relativeTarget),
104
- ];
105
- }
106
-
107
- function copyAgentFiles(targetDir, selectedAgents) {
108
- const copied = [];
109
- for (const key of selectedAgents) {
110
- const adapter = ADAPTERS[key];
111
- if (!adapter) continue;
112
- copyFile(adapter.source, path.join(targetDir, adapter.target));
113
- copied.push(adapter.target);
114
- }
115
- return copied;
116
- }
117
-
118
- function normalizeAgents(agentKeys) {
119
- return Array.from(new Set(agentKeys.filter((key) => ADAPTERS[key])));
120
- }
121
-
122
- function createInterface() {
123
- return readline.createInterface({ input: process.stdin, output: process.stdout });
124
- }
125
-
126
- function ask(rl, question) {
127
- return new Promise((resolve) => rl.question(question, resolve));
128
- }
129
-
130
- async function runInteractive(defaults) {
131
- const rl = createInterface();
132
- try {
133
- console.log('\nskill-reyson interactive installer\n');
134
- const dirAnswer = await ask(rl, `Target directory [${defaults.dir}]: `);
135
- const targetDir = path.resolve(dirAnswer.trim() || defaults.dir);
136
-
137
- const includeAgentAnswer = await ask(rl, 'Install agent guidance files (AGENTS.md / CLAUDE.md / RULES.md)? [y/N]: ');
138
- const withAgentFiles = /^y(es)?$/i.test(includeAgentAnswer.trim());
139
-
140
- let agents = [];
141
- if (withAgentFiles) {
142
- console.log('\nSelect agent adapters (comma-separated numbers):');
143
- console.log(' 1) Codex -> AGENTS.md');
144
- console.log(' 2) Claude Code -> CLAUDE.md');
145
- console.log(' 3) Generic rules -> RULES.md');
146
- const agentAnswer = await ask(rl, 'Choice(s) [1]: ');
147
- const tokens = (agentAnswer.trim() || '1').split(',').map((s) => s.trim());
148
- const mapping = { '1': 'codex', '2': 'claude', '3': 'generic' };
149
- agents = normalizeAgents(tokens.map((token) => mapping[token] || token.toLowerCase()));
150
- if (agents.length === 0) {
151
- agents = ['codex'];
152
- }
153
- }
154
-
155
- const confirmation = await ask(rl, `\nProceed installing into ${targetDir}? [Y/n]: `);
156
- const ok = confirmation.trim() === '' || /^y(es)?$/i.test(confirmation.trim());
157
- if (!ok) {
158
- console.log('Installation cancelled.');
159
- return;
160
- }
161
-
162
- const result = performInstall({ targetDir, withAgentFiles, agents });
163
- printSummary(result);
164
- } finally {
165
- rl.close();
166
- }
167
- }
168
-
169
- function performInstall({ targetDir, withAgentFiles, agents }) {
170
- ensureDir(targetDir);
171
- const coreFiles = copyCoreArtifacts(targetDir);
172
- const agentFiles = withAgentFiles ? copyAgentFiles(targetDir, normalizeAgents(agents)) : [];
173
- return { targetDir, coreFiles, agentFiles };
174
- }
175
-
176
- function printSummary(result) {
177
- console.log('\nInstalled skill-reyson scaffold:\n');
178
- console.log(`Target: ${result.targetDir}`);
179
- console.log('\nCore files:');
180
- for (const file of result.coreFiles) {
181
- console.log(` - ${file}`);
182
- }
183
- if (result.agentFiles.length > 0) {
184
- console.log('\nAgent guidance files:');
185
- for (const file of result.agentFiles) {
186
- console.log(` - ${file}`);
187
- }
188
- } else {
189
- console.log('\nAgent guidance files: none (default)');
190
- }
191
- console.log('\nNext steps:');
192
- console.log(' 1) Open docs/spec-workflow.md');
193
- console.log(' 2) Ensure your agent knows to read the workflow before coding');
194
- console.log(' 3) Use generate-task-list and generate-checklist when artifacts are missing');
195
- }
196
-
197
- async function main() {
198
- let options;
199
- try {
200
- options = parseArgs(process.argv);
201
- } catch (error) {
202
- console.error(error.message);
203
- printHelp();
204
- process.exit(1);
205
- }
206
-
207
- if (options.command === 'help' || options.command === '--help' || options.command === '-h') {
208
- printHelp();
209
- return;
210
- }
211
-
212
- if (options.command !== 'install') {
213
- console.error(`Unknown command: ${options.command}`);
214
- printHelp();
215
- process.exit(1);
216
- }
217
-
218
- if (options.yes) {
219
- const result = performInstall({
220
- targetDir: options.dir,
221
- withAgentFiles: options.withAgentFiles,
222
- agents: options.agents,
223
- });
224
- printSummary(result);
225
- return;
226
- }
227
-
228
- await runInteractive(options);
229
- }
230
-
231
- main().catch((error) => {
232
- console.error(error.stack || error.message);
233
- process.exit(1);
234
- });
2
+ require('./reyson-spec-gate.js');
package/package.json CHANGED
@@ -1,10 +1,11 @@
1
1
  {
2
2
  "name": "reyson-spec-gate",
3
- "version": "0.1.0",
3
+ "version": "0.1.1",
4
4
  "description": "Interactive installer for a spec-first workflow scaffold with docs, skills, and optional agent guidance files.",
5
5
  "type": "commonjs",
6
6
  "bin": {
7
- "skill-reyson": "bin/skill-reyson.js"
7
+ "reyson-spec-gate": "bin/reyson-spec-gate.js",
8
+ "skill-reyson": "bin/reyson-spec-gate.js"
8
9
  },
9
10
  "files": [
10
11
  "bin",
@@ -1,16 +0,0 @@
1
- # AGENTS.md
2
-
3
- ## Spec-first workflow rules
4
-
5
- Before any implementation task, read `docs/spec-workflow.md`.
6
-
7
- Before coding begins, verify whether the current work includes:
8
- - an explicit task list
9
- - an explicit checklist
10
-
11
- If the task list is missing, generate it first.
12
- If the checklist is missing, generate it second.
13
- If both are missing, generate both before coding.
14
-
15
- Do not begin implementation until the pre-coding gate is satisfied.
16
- After coding, revisit the checklist before claiming completion.
@@ -1,16 +0,0 @@
1
- # CLAUDE.md
2
-
3
- ## Spec-first workflow rules
4
-
5
- Before any implementation task, read `docs/spec-workflow.md`.
6
-
7
- Before coding begins, verify whether the current work includes:
8
- - an explicit task list
9
- - an explicit checklist
10
-
11
- If the task list is missing, generate it first.
12
- If the checklist is missing, generate it second.
13
- If both are missing, generate both before coding.
14
-
15
- Do not begin implementation until the pre-coding gate is satisfied.
16
- After coding, revisit the checklist before claiming completion.
File without changes