conductor-4-all 0.0.4 → 0.0.5

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,6 +1,12 @@
1
1
  # Conductor for All
2
2
 
3
- **Conductor for All** is a standalone command-line tool designed to bring the [Conductor](https://github.com/google/labs-prototypes/tree/main/gemini-cli) spec-driven development methodology to *any* coding environment.
3
+ [![npm version](https://badge.fury.io/js/conductor-4-all.svg)](https://badge.fury.io/js/conductor-4-all)
4
+
5
+ <img src="./conductor_banner.png" height="400" alt="Conductor for All Banner" />
6
+
7
+ [English](./README.md) | [中文](./README_zh.md) | [日本語](./README_ja.md) | [한국어](./README_ko.md)
8
+
9
+ **Conductor for All** is a standalone command-line tool designed to bring the [Conductor](https://github.com/gemini-cli-extensions/conductor) spec-driven development methodology to *any* coding environment.
4
10
 
5
11
  Originally tied to the Gemini CLI extension, this project aims to decouple the methodology, allowing developers to install and initialize Conductor workflows in their projects so they can be leveraged by **any** AI Coding Agent (e.g., Claude Code, Cline, Cursor, Windsurf) or IDE.
6
12
 
@@ -12,36 +18,29 @@ Originally tied to the Gemini CLI extension, this project aims to decouple the m
12
18
 
13
19
  ## 🚀 Usage
14
20
 
15
- ### 1. Installation
16
-
17
- #### Global Installation via npm (Recommended)
18
-
19
- ```bash
20
- npm install -g conductor-4-all
21
- ```
21
+ ### 1. Setup Conductor in Your Project
22
22
 
23
- #### From Source
23
+ To initialize Conductor in your project, simply run the following command in your project root:
24
24
 
25
25
  ```bash
26
- npm install
27
- npm run build
26
+ npx conductor-4-all install
28
27
  ```
29
28
 
30
- ### 2. Setup Conductor in Your Project
29
+ ### 2. Alternative: Build from Source
31
30
 
32
- Run the `install` command in the root of your project:
31
+ If you prefer to build from source:
33
32
 
34
33
  ```bash
35
- # If installed globally:
36
- conductor install
37
-
38
- # If built from source:
34
+ pnpm install
35
+ pnpm build
39
36
  node dist/index.js install
40
37
  ```
41
38
 
42
39
  You will be prompted to select your AI Coding Agent:
43
40
  - **Opencode**
44
41
  - **Claude Code**
42
+ - **Antigravity**
43
+ - **Cursor**
45
44
 
46
45
  This will verify the environment and install the necessary Conductor files:
47
46
  - **Commands:** Agent-specific prompt files (e.g., `.opencode/commands/conductor:setup.md`) that your agent can execute.
@@ -58,19 +57,8 @@ Once installed, you can instruct your AI Agent to perform Conductor tasks using
58
57
 
59
58
  *Note: The exact invocation syntax depends on your specific agent's slash command or file context capabilities.*
60
59
 
61
- ## 🛠️ Contribution Guide
62
-
63
- We follow a strict spec-driven development workflow ourselves!
64
-
65
- - **Workflow:** Please read [`conductor/workflow.md`](./conductor/workflow.md) for our detailed development protocols (Tasks, TDD, Commits).
66
- - **Tech Stack:** Check [`conductor/tech-stack.md`](./conductor/tech-stack.md) for approved technologies (TypeScript/Node.js).
67
- - **Product Guidelines:** See [`conductor/product-guidelines.md`](./conductor/product-guidelines.md) for design philosophy.
68
60
 
69
- To start contributing:
70
- 1. Read the docs above.
71
- 2. Pick a task from `conductor/tracks.md` (or propose one).
72
- 3. Follow the **Conductor Workflow** to implement it.
73
61
 
74
62
  ## 🙏 Acknowledgements
75
63
 
76
- This project is inspired by and based on the **Conductor** methodology originally developed for the **Gemini CLI**. We aim to extend its benefits to the broader developer ecosystem.
64
+ This project is inspired by and based on the [Conductor](https://github.com/gemini-cli-extensions/conductor) methodology originally developed for the **Gemini CLI**. We aim to extend its benefits to the broader developer ecosystem.
package/dist/index.cjs CHANGED
@@ -23,7 +23,7 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
23
23
  mod
24
24
  ));
25
25
 
26
- // node_modules/tsup/assets/cjs_shims.js
26
+ // node_modules/.pnpm/tsup@8.5.1_postcss@8.5.6_typescript@5.9.3/node_modules/tsup/assets/cjs_shims.js
27
27
  var getImportMetaUrl = () => typeof document === "undefined" ? new URL(`file:${__filename}`).href : document.currentScript && document.currentScript.tagName.toUpperCase() === "SCRIPT" ? document.currentScript.src : new URL("main.js", document.baseURI).href;
28
28
  var importMetaUrl = /* @__PURE__ */ getImportMetaUrl();
29
29
 
@@ -51,6 +51,11 @@ async function promptForAgent() {
51
51
  name: "Antigravity",
52
52
  value: "antigravity",
53
53
  description: "Google's agentic coding assistant"
54
+ },
55
+ {
56
+ name: "Cursor",
57
+ value: "cursor",
58
+ description: "Cursor IDE's AI agent"
54
59
  }
55
60
  ],
56
61
  default: "opencode"
@@ -58,9 +63,9 @@ async function promptForAgent() {
58
63
  return answer;
59
64
  }
60
65
 
61
- // src/utils/install.ts
62
- var import_fs_extra = __toESM(require("fs-extra"), 1);
66
+ // src/generators/ConfigurableGenerator.ts
63
67
  var import_path2 = require("path");
68
+ var import_fs_extra = __toESM(require("fs-extra"), 1);
64
69
  var import_smol_toml = require("smol-toml");
65
70
 
66
71
  // src/utils/template.ts
@@ -99,97 +104,160 @@ async function loadTemplate(templatePath) {
99
104
  return (0, import_promises.readFile)(fullPath, "utf-8");
100
105
  }
101
106
 
102
- // src/utils/install.ts
107
+ // src/generators/ConfigurableGenerator.ts
103
108
  var { existsSync, ensureDir, writeFile, copy } = import_fs_extra.default;
104
- async function validateProjectDirectory(targetDir, agentType) {
105
- if (!existsSync(targetDir)) {
106
- throw new Error(`Target directory does not exist: ${targetDir}`);
107
- }
108
- let agentDir;
109
- let setupFile;
110
- if (agentType === "claude-code") {
111
- agentDir = ".claude";
112
- setupFile = (0, import_path2.join)(targetDir, agentDir, "commands", "conductor:setup.md");
113
- } else if (agentType === "antigravity") {
114
- agentDir = ".agent";
115
- setupFile = (0, import_path2.join)(targetDir, agentDir, "workflows", "conductor:setup.md");
116
- } else {
117
- agentDir = ".opencode";
118
- setupFile = (0, import_path2.join)(targetDir, agentDir, "commands", "conductor:setup.md");
119
- }
120
- const agentPath = (0, import_path2.join)(targetDir, agentDir);
121
- const conductorPath = (0, import_path2.join)(agentPath, "conductor");
122
- if (existsSync(conductorPath) && existsSync(setupFile)) {
123
- throw new Error(`Conductor (${agentType}) is already installed in: ${targetDir}`);
124
- }
125
- return targetDir;
126
- }
127
- async function createConductorDirectories(targetDir, agentType) {
128
- let agentDir;
129
- let commandsDir;
130
- if (agentType === "claude-code") {
131
- agentDir = ".claude";
132
- commandsDir = "commands";
133
- } else if (agentType === "antigravity") {
134
- agentDir = ".agent";
135
- commandsDir = "workflows";
136
- } else {
137
- agentDir = ".opencode";
138
- commandsDir = "commands";
139
- }
140
- const agentPath = (0, import_path2.join)(targetDir, agentDir);
141
- await ensureDir((0, import_path2.join)(agentPath, commandsDir));
142
- await ensureDir((0, import_path2.join)(agentPath, "conductor"));
143
- }
144
- async function copyTemplateFiles(targetDir, agentType) {
145
- const commands = ["setup", "newTrack", "implement", "status", "revert"];
146
- let agentDir;
147
- let commandsDir;
148
- if (agentType === "claude-code") {
149
- agentDir = ".claude";
150
- commandsDir = "commands";
151
- } else if (agentType === "antigravity") {
152
- agentDir = ".agent";
153
- commandsDir = "workflows";
154
- } else {
155
- agentDir = ".opencode";
156
- commandsDir = "commands";
157
- }
158
- const agentPath = (0, import_path2.join)(targetDir, agentDir);
159
- const targetCommandsDir = (0, import_path2.join)(agentPath, commandsDir);
160
- const templateRoot = await getTemplateRoot();
161
- const installPath = (0, import_path2.join)(agentDir, "conductor");
162
- try {
163
- const templateSource = (0, import_path2.join)(templateRoot, "templates");
164
- const templateDest = (0, import_path2.join)(agentPath, "conductor", "templates");
165
- await copy(templateSource, templateDest);
166
- } catch (e) {
167
- console.warn("Failed to copy templates directory:", e);
109
+ function processTemplateContent(tomlContent, installPath, agentType) {
110
+ const parsed = (0, import_smol_toml.parse)(tomlContent);
111
+ if (!parsed.prompt) {
112
+ return null;
168
113
  }
169
- for (const cmd of commands) {
170
- try {
171
- const tomlContent = await loadTemplate(`commands/${cmd}.toml`);
172
- let finalContent;
173
- let fileName;
174
- const parsed = (0, import_smol_toml.parse)(tomlContent);
175
- if (!parsed.prompt) {
176
- console.warn(`Warning: No prompt found in ${cmd}.toml`);
177
- continue;
178
- }
179
- let prompt = parsed.prompt;
180
- prompt = prompt.replace(/__\$\$CODE_AGENT_INSTALL_PATH\$\$__/g, installPath);
181
- finalContent = substituteVariables(prompt, { agent_type: agentType });
182
- if (parsed.description) {
183
- finalContent = `---
114
+ let prompt = parsed.prompt;
115
+ prompt = prompt.replace(/__\$\$CODE_AGENT_INSTALL_PATH\$\$__/g, installPath);
116
+ const finalContent = substituteVariables(prompt, { agent_type: agentType });
117
+ if (parsed.description) {
118
+ return `---
184
119
  description: ${parsed.description}
185
120
  ---
186
121
  ${finalContent}`;
187
- }
188
- fileName = `conductor:${cmd}.md`;
189
- await writeFile((0, import_path2.join)(targetCommandsDir, fileName), finalContent);
122
+ }
123
+ return finalContent;
124
+ }
125
+ var ConfigurableGenerator = class {
126
+ constructor(config) {
127
+ this.config = config;
128
+ }
129
+ async validate(targetDir) {
130
+ if (!existsSync(targetDir)) {
131
+ throw new Error(`Target directory does not exist: ${targetDir}`);
132
+ }
133
+ const { agentDir, commandsDir, displayName } = this.config;
134
+ const setupFile = (0, import_path2.join)(targetDir, agentDir, commandsDir, "conductor:setup.md");
135
+ const conductorPath = (0, import_path2.join)(targetDir, agentDir, "conductor");
136
+ if (existsSync(conductorPath) && existsSync(setupFile)) {
137
+ throw new Error(`Conductor (${displayName}) is already installed in: ${targetDir}`);
138
+ }
139
+ return targetDir;
140
+ }
141
+ async generate(targetDir) {
142
+ const { agentDir, commandsDir, agentType } = this.config;
143
+ const agentPath = (0, import_path2.join)(targetDir, agentDir);
144
+ const targetCommandsDir = (0, import_path2.join)(agentPath, commandsDir);
145
+ const installPath = (0, import_path2.join)(agentDir, "conductor");
146
+ await ensureDir(targetCommandsDir);
147
+ await ensureDir((0, import_path2.join)(agentPath, "conductor"));
148
+ const templateRoot = await getTemplateRoot();
149
+ try {
150
+ const templateSource = (0, import_path2.join)(templateRoot, "templates");
151
+ const templateDest = (0, import_path2.join)(agentPath, "conductor", "templates");
152
+ await copy(templateSource, templateDest);
190
153
  } catch (e) {
191
- console.warn(`Failed to process ${cmd}:`, e);
154
+ console.warn("Failed to copy templates directory:", e);
192
155
  }
156
+ const commands = ["setup", "newTrack", "implement", "status", "revert"];
157
+ for (const cmd of commands) {
158
+ try {
159
+ const tomlContent = await loadTemplate(`commands/${cmd}.toml`);
160
+ const finalContent = processTemplateContent(tomlContent, installPath, agentType);
161
+ if (finalContent) {
162
+ const fileName = `conductor:${cmd}.md`;
163
+ await writeFile((0, import_path2.join)(targetCommandsDir, fileName), finalContent);
164
+ }
165
+ } catch (e) {
166
+ console.warn(`Failed to process ${cmd}:`, e);
167
+ }
168
+ }
169
+ }
170
+ };
171
+
172
+ // src/generators/factory.ts
173
+ function createGenerator(config) {
174
+ return new ConfigurableGenerator(config);
175
+ }
176
+
177
+ // src/generators/config.ts
178
+ var AGENT_CONFIGS = {
179
+ opencode: {
180
+ agentType: "opencode",
181
+ agentDir: ".opencode",
182
+ commandsDir: "commands",
183
+ displayName: "OpenCode"
184
+ },
185
+ "claude-code": {
186
+ agentType: "claude-code",
187
+ agentDir: ".claude",
188
+ commandsDir: "commands",
189
+ displayName: "Claude Code"
190
+ },
191
+ antigravity: {
192
+ agentType: "antigravity",
193
+ agentDir: ".agent",
194
+ commandsDir: "workflows",
195
+ displayName: "Antigravity"
196
+ },
197
+ cursor: {
198
+ agentType: "cursor",
199
+ agentDir: ".cursor",
200
+ commandsDir: "commands",
201
+ displayName: "Cursor"
202
+ }
203
+ };
204
+
205
+ // src/generators/OpenCodeGenerator.ts
206
+ var OpenCodeGenerator = class {
207
+ generator = createGenerator(AGENT_CONFIGS.opencode);
208
+ validate(targetDir) {
209
+ return this.generator.validate(targetDir);
210
+ }
211
+ generate(targetDir) {
212
+ return this.generator.generate(targetDir);
213
+ }
214
+ };
215
+
216
+ // src/generators/ClaudeCodeGenerator.ts
217
+ var ClaudeCodeGenerator = class {
218
+ generator = createGenerator(AGENT_CONFIGS["claude-code"]);
219
+ validate(targetDir) {
220
+ return this.generator.validate(targetDir);
221
+ }
222
+ generate(targetDir) {
223
+ return this.generator.generate(targetDir);
224
+ }
225
+ };
226
+
227
+ // src/generators/AntigravityGenerator.ts
228
+ var AntigravityGenerator = class {
229
+ generator = createGenerator(AGENT_CONFIGS.antigravity);
230
+ validate(targetDir) {
231
+ return this.generator.validate(targetDir);
232
+ }
233
+ generate(targetDir) {
234
+ return this.generator.generate(targetDir);
235
+ }
236
+ };
237
+
238
+ // src/generators/CursorGenerator.ts
239
+ var CursorGenerator = class {
240
+ generator = createGenerator(AGENT_CONFIGS.cursor);
241
+ validate(targetDir) {
242
+ return this.generator.validate(targetDir);
243
+ }
244
+ generate(targetDir) {
245
+ return this.generator.generate(targetDir);
246
+ }
247
+ };
248
+
249
+ // src/generators/index.ts
250
+ function getGenerator(agentType) {
251
+ switch (agentType) {
252
+ case "claude-code":
253
+ return new ClaudeCodeGenerator();
254
+ case "antigravity":
255
+ return new AntigravityGenerator();
256
+ case "cursor":
257
+ return new CursorGenerator();
258
+ case "opencode":
259
+ default:
260
+ return new OpenCodeGenerator();
193
261
  }
194
262
  }
195
263
 
@@ -202,15 +270,13 @@ async function installHandler(argv) {
202
270
  console.log("Step 1: Prompting for agent selection...");
203
271
  const agent = await promptForAgent();
204
272
  console.log(`\u2714 Selected agent: ${agent}`);
273
+ const generator = getGenerator(agent);
205
274
  console.log("\nStep 2: Validating project directory...");
206
- const validatedPath = await validateProjectDirectory(targetDir, agent);
275
+ const validatedPath = await generator.validate(targetDir);
207
276
  console.log(`\u2714 Validation complete: ${validatedPath}`);
208
- console.log("\nStep 3: Creating Conductor directories...");
209
- await createConductorDirectories(validatedPath, agent);
210
- console.log("\u2714 Directories created");
211
- console.log("\nStep 4: Copying template files...");
212
- await copyTemplateFiles(validatedPath, agent);
213
- console.log("\u2714 Templates copied");
277
+ console.log("\nStep 3: Generating files...");
278
+ await generator.generate(validatedPath);
279
+ console.log("\u2714 Files generated");
214
280
  console.log("\n\u2714 Conductor initialized successfully!");
215
281
  } catch (err) {
216
282
  console.error("\n\u2718 Installation failed:", err instanceof Error ? err.message : err);
package/dist/index.js CHANGED
@@ -24,6 +24,11 @@ async function promptForAgent() {
24
24
  name: "Antigravity",
25
25
  value: "antigravity",
26
26
  description: "Google's agentic coding assistant"
27
+ },
28
+ {
29
+ name: "Cursor",
30
+ value: "cursor",
31
+ description: "Cursor IDE's AI agent"
27
32
  }
28
33
  ],
29
34
  default: "opencode"
@@ -31,9 +36,9 @@ async function promptForAgent() {
31
36
  return answer;
32
37
  }
33
38
 
34
- // src/utils/install.ts
35
- import fs from "fs-extra";
39
+ // src/generators/ConfigurableGenerator.ts
36
40
  import { join as join2 } from "path";
41
+ import fs from "fs-extra";
37
42
  import { parse } from "smol-toml";
38
43
 
39
44
  // src/utils/template.ts
@@ -72,97 +77,160 @@ async function loadTemplate(templatePath) {
72
77
  return readFile(fullPath, "utf-8");
73
78
  }
74
79
 
75
- // src/utils/install.ts
80
+ // src/generators/ConfigurableGenerator.ts
76
81
  var { existsSync, ensureDir, writeFile, copy } = fs;
77
- async function validateProjectDirectory(targetDir, agentType) {
78
- if (!existsSync(targetDir)) {
79
- throw new Error(`Target directory does not exist: ${targetDir}`);
80
- }
81
- let agentDir;
82
- let setupFile;
83
- if (agentType === "claude-code") {
84
- agentDir = ".claude";
85
- setupFile = join2(targetDir, agentDir, "commands", "conductor:setup.md");
86
- } else if (agentType === "antigravity") {
87
- agentDir = ".agent";
88
- setupFile = join2(targetDir, agentDir, "workflows", "conductor:setup.md");
89
- } else {
90
- agentDir = ".opencode";
91
- setupFile = join2(targetDir, agentDir, "commands", "conductor:setup.md");
92
- }
93
- const agentPath = join2(targetDir, agentDir);
94
- const conductorPath = join2(agentPath, "conductor");
95
- if (existsSync(conductorPath) && existsSync(setupFile)) {
96
- throw new Error(`Conductor (${agentType}) is already installed in: ${targetDir}`);
97
- }
98
- return targetDir;
99
- }
100
- async function createConductorDirectories(targetDir, agentType) {
101
- let agentDir;
102
- let commandsDir;
103
- if (agentType === "claude-code") {
104
- agentDir = ".claude";
105
- commandsDir = "commands";
106
- } else if (agentType === "antigravity") {
107
- agentDir = ".agent";
108
- commandsDir = "workflows";
109
- } else {
110
- agentDir = ".opencode";
111
- commandsDir = "commands";
112
- }
113
- const agentPath = join2(targetDir, agentDir);
114
- await ensureDir(join2(agentPath, commandsDir));
115
- await ensureDir(join2(agentPath, "conductor"));
116
- }
117
- async function copyTemplateFiles(targetDir, agentType) {
118
- const commands = ["setup", "newTrack", "implement", "status", "revert"];
119
- let agentDir;
120
- let commandsDir;
121
- if (agentType === "claude-code") {
122
- agentDir = ".claude";
123
- commandsDir = "commands";
124
- } else if (agentType === "antigravity") {
125
- agentDir = ".agent";
126
- commandsDir = "workflows";
127
- } else {
128
- agentDir = ".opencode";
129
- commandsDir = "commands";
130
- }
131
- const agentPath = join2(targetDir, agentDir);
132
- const targetCommandsDir = join2(agentPath, commandsDir);
133
- const templateRoot = await getTemplateRoot();
134
- const installPath = join2(agentDir, "conductor");
135
- try {
136
- const templateSource = join2(templateRoot, "templates");
137
- const templateDest = join2(agentPath, "conductor", "templates");
138
- await copy(templateSource, templateDest);
139
- } catch (e) {
140
- console.warn("Failed to copy templates directory:", e);
82
+ function processTemplateContent(tomlContent, installPath, agentType) {
83
+ const parsed = parse(tomlContent);
84
+ if (!parsed.prompt) {
85
+ return null;
141
86
  }
142
- for (const cmd of commands) {
143
- try {
144
- const tomlContent = await loadTemplate(`commands/${cmd}.toml`);
145
- let finalContent;
146
- let fileName;
147
- const parsed = parse(tomlContent);
148
- if (!parsed.prompt) {
149
- console.warn(`Warning: No prompt found in ${cmd}.toml`);
150
- continue;
151
- }
152
- let prompt = parsed.prompt;
153
- prompt = prompt.replace(/__\$\$CODE_AGENT_INSTALL_PATH\$\$__/g, installPath);
154
- finalContent = substituteVariables(prompt, { agent_type: agentType });
155
- if (parsed.description) {
156
- finalContent = `---
87
+ let prompt = parsed.prompt;
88
+ prompt = prompt.replace(/__\$\$CODE_AGENT_INSTALL_PATH\$\$__/g, installPath);
89
+ const finalContent = substituteVariables(prompt, { agent_type: agentType });
90
+ if (parsed.description) {
91
+ return `---
157
92
  description: ${parsed.description}
158
93
  ---
159
94
  ${finalContent}`;
160
- }
161
- fileName = `conductor:${cmd}.md`;
162
- await writeFile(join2(targetCommandsDir, fileName), finalContent);
95
+ }
96
+ return finalContent;
97
+ }
98
+ var ConfigurableGenerator = class {
99
+ constructor(config) {
100
+ this.config = config;
101
+ }
102
+ async validate(targetDir) {
103
+ if (!existsSync(targetDir)) {
104
+ throw new Error(`Target directory does not exist: ${targetDir}`);
105
+ }
106
+ const { agentDir, commandsDir, displayName } = this.config;
107
+ const setupFile = join2(targetDir, agentDir, commandsDir, "conductor:setup.md");
108
+ const conductorPath = join2(targetDir, agentDir, "conductor");
109
+ if (existsSync(conductorPath) && existsSync(setupFile)) {
110
+ throw new Error(`Conductor (${displayName}) is already installed in: ${targetDir}`);
111
+ }
112
+ return targetDir;
113
+ }
114
+ async generate(targetDir) {
115
+ const { agentDir, commandsDir, agentType } = this.config;
116
+ const agentPath = join2(targetDir, agentDir);
117
+ const targetCommandsDir = join2(agentPath, commandsDir);
118
+ const installPath = join2(agentDir, "conductor");
119
+ await ensureDir(targetCommandsDir);
120
+ await ensureDir(join2(agentPath, "conductor"));
121
+ const templateRoot = await getTemplateRoot();
122
+ try {
123
+ const templateSource = join2(templateRoot, "templates");
124
+ const templateDest = join2(agentPath, "conductor", "templates");
125
+ await copy(templateSource, templateDest);
163
126
  } catch (e) {
164
- console.warn(`Failed to process ${cmd}:`, e);
127
+ console.warn("Failed to copy templates directory:", e);
165
128
  }
129
+ const commands = ["setup", "newTrack", "implement", "status", "revert"];
130
+ for (const cmd of commands) {
131
+ try {
132
+ const tomlContent = await loadTemplate(`commands/${cmd}.toml`);
133
+ const finalContent = processTemplateContent(tomlContent, installPath, agentType);
134
+ if (finalContent) {
135
+ const fileName = `conductor:${cmd}.md`;
136
+ await writeFile(join2(targetCommandsDir, fileName), finalContent);
137
+ }
138
+ } catch (e) {
139
+ console.warn(`Failed to process ${cmd}:`, e);
140
+ }
141
+ }
142
+ }
143
+ };
144
+
145
+ // src/generators/factory.ts
146
+ function createGenerator(config) {
147
+ return new ConfigurableGenerator(config);
148
+ }
149
+
150
+ // src/generators/config.ts
151
+ var AGENT_CONFIGS = {
152
+ opencode: {
153
+ agentType: "opencode",
154
+ agentDir: ".opencode",
155
+ commandsDir: "commands",
156
+ displayName: "OpenCode"
157
+ },
158
+ "claude-code": {
159
+ agentType: "claude-code",
160
+ agentDir: ".claude",
161
+ commandsDir: "commands",
162
+ displayName: "Claude Code"
163
+ },
164
+ antigravity: {
165
+ agentType: "antigravity",
166
+ agentDir: ".agent",
167
+ commandsDir: "workflows",
168
+ displayName: "Antigravity"
169
+ },
170
+ cursor: {
171
+ agentType: "cursor",
172
+ agentDir: ".cursor",
173
+ commandsDir: "commands",
174
+ displayName: "Cursor"
175
+ }
176
+ };
177
+
178
+ // src/generators/OpenCodeGenerator.ts
179
+ var OpenCodeGenerator = class {
180
+ generator = createGenerator(AGENT_CONFIGS.opencode);
181
+ validate(targetDir) {
182
+ return this.generator.validate(targetDir);
183
+ }
184
+ generate(targetDir) {
185
+ return this.generator.generate(targetDir);
186
+ }
187
+ };
188
+
189
+ // src/generators/ClaudeCodeGenerator.ts
190
+ var ClaudeCodeGenerator = class {
191
+ generator = createGenerator(AGENT_CONFIGS["claude-code"]);
192
+ validate(targetDir) {
193
+ return this.generator.validate(targetDir);
194
+ }
195
+ generate(targetDir) {
196
+ return this.generator.generate(targetDir);
197
+ }
198
+ };
199
+
200
+ // src/generators/AntigravityGenerator.ts
201
+ var AntigravityGenerator = class {
202
+ generator = createGenerator(AGENT_CONFIGS.antigravity);
203
+ validate(targetDir) {
204
+ return this.generator.validate(targetDir);
205
+ }
206
+ generate(targetDir) {
207
+ return this.generator.generate(targetDir);
208
+ }
209
+ };
210
+
211
+ // src/generators/CursorGenerator.ts
212
+ var CursorGenerator = class {
213
+ generator = createGenerator(AGENT_CONFIGS.cursor);
214
+ validate(targetDir) {
215
+ return this.generator.validate(targetDir);
216
+ }
217
+ generate(targetDir) {
218
+ return this.generator.generate(targetDir);
219
+ }
220
+ };
221
+
222
+ // src/generators/index.ts
223
+ function getGenerator(agentType) {
224
+ switch (agentType) {
225
+ case "claude-code":
226
+ return new ClaudeCodeGenerator();
227
+ case "antigravity":
228
+ return new AntigravityGenerator();
229
+ case "cursor":
230
+ return new CursorGenerator();
231
+ case "opencode":
232
+ default:
233
+ return new OpenCodeGenerator();
166
234
  }
167
235
  }
168
236
 
@@ -175,15 +243,13 @@ async function installHandler(argv) {
175
243
  console.log("Step 1: Prompting for agent selection...");
176
244
  const agent = await promptForAgent();
177
245
  console.log(`\u2714 Selected agent: ${agent}`);
246
+ const generator = getGenerator(agent);
178
247
  console.log("\nStep 2: Validating project directory...");
179
- const validatedPath = await validateProjectDirectory(targetDir, agent);
248
+ const validatedPath = await generator.validate(targetDir);
180
249
  console.log(`\u2714 Validation complete: ${validatedPath}`);
181
- console.log("\nStep 3: Creating Conductor directories...");
182
- await createConductorDirectories(validatedPath, agent);
183
- console.log("\u2714 Directories created");
184
- console.log("\nStep 4: Copying template files...");
185
- await copyTemplateFiles(validatedPath, agent);
186
- console.log("\u2714 Templates copied");
250
+ console.log("\nStep 3: Generating files...");
251
+ await generator.generate(validatedPath);
252
+ console.log("\u2714 Files generated");
187
253
  console.log("\n\u2714 Conductor initialized successfully!");
188
254
  } catch (err) {
189
255
  console.error("\n\u2718 Installation failed:", err instanceof Error ? err.message : err);
package/package.json CHANGED
@@ -1,12 +1,16 @@
1
1
  {
2
2
  "name": "conductor-4-all",
3
- "version": "0.0.4",
3
+ "version": "0.0.5",
4
4
  "description": "Conductor spec-driven development CLI - TypeScript/Node.js version",
5
5
  "repository": {
6
6
  "type": "git",
7
7
  "url": "git+https://github.com/hlhr202/Conductor-for-all.git"
8
8
  },
9
9
  "homepage": "https://github.com/hlhr202/Conductor-for-all",
10
+ "packageManager": "pnpm@10.24.0",
11
+ "engines": {
12
+ "node": ">=18"
13
+ },
10
14
  "type": "module",
11
15
  "bin": {
12
16
  "conductor": "./dist/index.js",