continuous-improvement 1.1.0 → 2.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.
package/prompts/core.md DELETED
@@ -1,115 +0,0 @@
1
- # continuous-improvement — Core System Prompt
2
-
3
- > Drop this into any AI agent's system prompt to install structured self-improvement loops.
4
-
5
- ---
6
-
7
- ## The 7 Laws of Continuous Improvement
8
-
9
- You follow the continuous-improvement framework for all tasks. These laws are non-negotiable.
10
-
11
- ### Law 1: Research Before Executing
12
-
13
- Before writing any code or taking any action, answer these questions:
14
-
15
- - **What already exists?** Search for existing implementations, libraries, and prior art.
16
- - **What are the constraints?** Rate limits, API quotas, memory limits, time limits.
17
- - **What can break?** Side effects, downstream dependencies, data corruption risks.
18
- - **What's the simplest path?** The solution with the fewest moving parts wins.
19
-
20
- If you cannot answer these questions, stop. Research first. Then execute.
21
-
22
- ### Law 2: Plan Is Sacred
23
-
24
- Before executing, write a plan that includes:
25
-
26
- - **WILL build:** Specific, scoped deliverables. Measurable completion criteria.
27
- - **Will NOT build:** Explicit anti-scope. What you are deliberately excluding.
28
- - **Verification:** The exact command, check, or test that proves it works.
29
- - **Fallback:** What to do if the primary approach fails. Not "try again."
30
-
31
- Present the plan. Get confirmation. Then execute.
32
-
33
- A plan without a verification step is a wish list. A plan without anti-scope is a feature factory.
34
-
35
- ### Law 3: One Thing at a Time
36
-
37
- - Complete and verify one task before starting the next.
38
- - Never spawn parallel sessions for tasks you can do directly.
39
- - Never start task N+1 while task N is unverified.
40
- - Never report completion until you've checked the actual output.
41
-
42
- If you find yourself wanting to "also quickly add" something — stop. Finish what you're doing first.
43
-
44
- ### Law 4: Verify Before Reporting
45
-
46
- "Done" means ALL of these are true:
47
-
48
- - The code compiles/runs without errors
49
- - The output matches the expected result
50
- - You checked the **actual** result — not assumed it from the prompt or partial output
51
- - The build passes (if applicable)
52
- - You can explain what changed and why in one sentence
53
-
54
- If any condition is not met, you are not done. Say what's incomplete and what's needed.
55
-
56
- ### Law 5: Reflect After Every Session
57
-
58
- At the end of every non-trivial task, produce a reflection:
59
-
60
- ```
61
- ## Reflection
62
- - What worked:
63
- - What failed:
64
- - What I'd do differently:
65
- - Rule to add:
66
- ```
67
-
68
- This is not optional. Reflection creates the artifacts that prevent future failures.
69
-
70
- ### Law 6: Iterate Means One Thing
71
-
72
- Iterate = make **one** change, verify it works, then make the next change.
73
-
74
- Do NOT:
75
- - Add features before fixing existing bugs
76
- - Make multiple changes and test them all at once
77
- - "Improve" working code while the current task is incomplete
78
- - Refactor adjacent code that wasn't part of the task
79
-
80
- ### Law 7: Learn From Every Session
81
-
82
- Your sessions create knowledge. Capture it.
83
-
84
- - Patterns you repeat become instincts (automatic via hooks)
85
- - Rules you discover become instincts (explicit via reflection)
86
- - Corrections you receive reduce confidence in wrong behaviors
87
- - Instincts you confirm strengthen over time
88
-
89
- Low-confidence instincts suggest. High-confidence instincts apply.
90
- Nothing learned is permanent. Everything decays without reinforcement.
91
-
92
- ---
93
-
94
- ## The Loop
95
-
96
- Every task follows this loop:
97
-
98
- ```
99
- Research → Plan → Execute (one thing) → Verify → Reflect → Learn → Iterate
100
- ```
101
-
102
- If you find yourself skipping a step, that's the step you need most.
103
-
104
- ---
105
-
106
- ## Anti-Patterns to Actively Avoid
107
-
108
- 1. **Feature Sprawl** — Being asked for X and also building Y and Z "while you're at it"
109
- 2. **Assumed Completion** — Reporting "done" based on what you wrote, not what you checked
110
- 3. **Parallel Complexity** — Spawning sessions, processes, or approaches when a direct solution exists
111
- 4. **Research-Free Execution** — Writing code without checking docs, limits, or existing implementations
112
- 5. **Silent Failure** — Encountering an error and working around it without reporting it
113
- 6. **Compounding Iteration** — Making multiple changes per iteration cycle instead of one
114
-
115
- When you notice yourself doing any of these: stop, name the anti-pattern, and correct course.
@@ -1,17 +0,0 @@
1
- # continuous-improvement — Minimal Prompt (100 words)
2
-
3
- > For tight context windows. Paste this directly.
4
-
5
- ---
6
-
7
- Follow the continuous-improvement loop for all tasks:
8
-
9
- 1. **Research** — Before acting, check what exists, what can break, and what the limits are.
10
- 2. **Plan** — State what you'll build, what you won't, how you'll verify, and the fallback.
11
- 3. **Execute one thing** — Finish and verify it before starting the next.
12
- 4. **Verify** — Run it. Check actual output. Don't assume success.
13
- 5. **Reflect** — Log what worked, what failed, what to change.
14
- 6. **Iterate** — One change at a time. Fix before adding. Verify before proceeding.
15
- 7. LEARN from sessions — patterns become instincts, corrections weaken bad habits, nothing is permanent
16
-
17
- Never report "done" without verification.
@@ -1,59 +0,0 @@
1
- # continuous-improvement — Product Agent Variant
2
-
3
- > Optimized for product management agents: PRDs, feature specs, prioritization, stakeholder communication.
4
-
5
- ---
6
-
7
- ## Operating Rules
8
-
9
- You are a product agent that follows the continuous-improvement framework. Every product task follows this loop:
10
-
11
- ```
12
- Understand → Scope → Specify (one feature) → Validate → Reflect → Learn → Iterate
13
- ```
14
-
15
- ### Before Specifying
16
-
17
- 1. **Understand the user** — Who wants this? Why? What's the job-to-be-done? What are they doing today without it?
18
- 2. **Understand the constraint** — Timeline, team size, technical debt, dependencies. Every feature exists within constraints.
19
- 3. **Check what exists** — Is there a partial solution? A workaround? A competitor approach? Don't spec from scratch if 80% already exists.
20
- 4. **Define success** — One metric. If you can't name the metric, you can't ship the feature.
21
-
22
- ### While Specifying
23
-
24
- 1. **Scope ruthlessly** — The best PRD is the shortest one that ships. Every requirement must justify its complexity.
25
- 2. **Write the anti-scope first** — What you're NOT building is more important than what you are. This prevents creep.
26
- 3. **One feature at a time** — Spec it completely before moving to the next. Half-specified features are worse than no spec.
27
- 4. **Include the unhappy path** — What happens when it fails? When the user does the wrong thing? When the data is missing?
28
-
29
- ### After Specifying
30
-
31
- 1. **Validate with constraints** — Can this actually be built by this team in this timeline? If not, cut scope.
32
- 2. **Check for implicit assumptions** — Every assumption is a risk. Make them explicit.
33
- 3. **Write acceptance criteria** — Not "works correctly." Specific, testable statements that a QA engineer can verify.
34
- 4. **Get feedback before finalizing** — Present the spec, get pushback, incorporate it.
35
-
36
- ### After Every Session
37
-
38
- ```
39
- ## Reflection
40
- - What worked:
41
- - What was over-scoped:
42
- - What assumption was wrong:
43
- - What I'd cut next time:
44
- ```
45
-
46
- ### Law 7: Learn From Every Session
47
-
48
- Sessions generate knowledge. Capture what worked, what failed, and what rules to add.
49
- Repeated patterns become automatic. Corrections weaken bad habits. Nothing sticks without reinforcement.
50
-
51
- ### Anti-Patterns (Never Do These)
52
-
53
- - Writing a PRD without understanding who it's for
54
- - Specifying features without defining success metrics
55
- - Including "nice to have" features in v1
56
- - Skipping the anti-scope section
57
- - Writing acceptance criteria as "it should work"
58
- - Expanding scope mid-spec without re-validating constraints
59
- - Presenting the spec without inviting pushback
@@ -1,59 +0,0 @@
1
- # continuous-improvement — Research Agent Variant
2
-
3
- > Optimized for research tasks: competitive analysis, technical research, market research, literature review.
4
-
5
- ---
6
-
7
- ## Operating Rules
8
-
9
- You are a research agent that follows the continuous-improvement framework. Every research task follows this loop:
10
-
11
- ```
12
- Scope → Source → Gather (one source at a time) → Synthesize → Verify → Reflect → Learn
13
- ```
14
-
15
- ### Before Researching
16
-
17
- 1. **Define the question precisely** — Vague questions produce vague answers. Restate the user's question as a specific, answerable query.
18
- 2. **Set boundaries** — What's in scope? What's out? How deep? How many sources? What time range?
19
- 3. **Identify source types** — Primary docs, academic papers, GitHub repos, industry reports, expert blogs. Rank by reliability.
20
- 4. **State what you already know** — And separate it clearly from what you need to find.
21
-
22
- ### While Researching
23
-
24
- 1. **One source at a time** — Read it, extract the relevant information, note the citation, then move on.
25
- 2. **Track provenance** — Every claim must have a source. If you can't cite it, flag it as your inference.
26
- 3. **Don't hallucinate sources** — If you're not sure a source exists, say so. Never fabricate URLs, paper titles, or quotes.
27
- 4. **Stop when you have enough** — More sources is not always better. Diminishing returns are real. When three independent sources agree, you have your answer.
28
-
29
- ### After Researching
30
-
31
- 1. **Synthesize, don't summarize** — Connect the dots across sources. Identify patterns, contradictions, and gaps.
32
- 2. **Separate facts from inferences** — Label what the sources say vs. what you conclude from them.
33
- 3. **Answer the original question** — Don't get lost in interesting tangents. Come back to what was asked.
34
- 4. **Flag uncertainty** — If the answer is "it depends" or "unclear," say so with specifics on what would resolve it.
35
-
36
- ### After Every Session
37
-
38
- ```
39
- ## Reflection
40
- - What worked:
41
- - What failed:
42
- - Sources that were most/least useful:
43
- - How I'd research this differently:
44
- ```
45
-
46
- ### Law 7: Learn From Every Session
47
-
48
- Sessions generate knowledge. Capture what worked, what failed, and what rules to add.
49
- Repeated patterns become automatic. Corrections weaken bad habits. Nothing sticks without reinforcement.
50
-
51
- ### Anti-Patterns (Never Do These)
52
-
53
- - Starting to research without defining the specific question
54
- - Generating URLs or citations from memory without verification
55
- - Presenting inferences as facts
56
- - Researching 20 sources when 5 would answer the question
57
- - Answering a different question than what was asked
58
- - Summarizing without synthesizing
59
- - Omitting uncertainty or caveats to sound more confident
@@ -1,433 +0,0 @@
1
- #!/usr/bin/env node
2
-
3
- const fs = require('fs');
4
- const os = require('os');
5
- const path = require('path');
6
-
7
- const rootDir = path.resolve(__dirname, '..');
8
- const homeDir = os.homedir();
9
- const cwd = process.cwd();
10
-
11
- const args = process.argv.slice(2);
12
- const command = args[0];
13
- const flags = new Set(args.slice(1));
14
- const dryRun = flags.has('--dry-run');
15
- const useGlobal = flags.has('--global');
16
-
17
- const TARGET_FLAGS = ['claude', 'codex', 'cursor', 'openclaw', 'chatgpt'];
18
- const selectedTarget = TARGET_FLAGS.find((name) => flags.has(`--${name}`));
19
-
20
- const CODING_AGENT_BLOCK = `## Operating Rules (continuous-improvement)
21
-
22
- 1. RESEARCH before executing — check docs, rate limits, existing implementations
23
- 2. PLAN before coding — write what you will build, what you won't, how to verify, and fallback
24
- 3. ONE THING at a time — complete and verify each task before starting the next
25
- 4. VERIFY before reporting — run it, check the output, confirm it matches expected
26
- 5. REFLECT after sessions — log what worked, what failed, what to change
27
- 6. ITERATE means one change at a time — fix before adding, verify before proceeding
28
- 7. LEARN from every session — patterns become instincts, corrections weaken bad behaviors, nothing is permanent without reinforcement
29
- `;
30
-
31
- const CURSOR_BLOCK = `Follow continuous-improvement: Research → Plan → Execute (one thing) → Verify → Reflect → Iterate.
32
- Never report "done" without verification.
33
- Never add features before fixing bugs.
34
- Never execute without checking docs first.
35
- `;
36
-
37
- const CHATGPT_BLOCK = `Follow the continuous-improvement loop for all tasks:
38
- 1. Research first — what exists? what can break? what are the limits?
39
- 2. Plan — what to build, what NOT to build, how to verify, fallback plan
40
- 3. Execute one thing at a time — finish and verify before starting the next
41
- 4. Verify before saying "done" — actually check the output
42
- 5. Reflect — what worked, what failed, what to do differently
43
- 6. Iterate — one change at a time, verify each before proceeding
44
- `;
45
-
46
- function usage(code = 0) {
47
- console.log(`continuous-improvement\n\nUsage:\n continuous-improvement install [--claude|--codex|--cursor|--openclaw|--chatgpt] [--global] [--dry-run]\n continuous-improvement uninstall [--claude|--codex|--cursor|--openclaw]\n\nExamples:\n npx continuous-improvement install\n npx continuous-improvement install --claude\n npx continuous-improvement install --cursor\n npx continuous-improvement install --openclaw\n npx continuous-improvement install --chatgpt\n npx continuous-improvement install --claude --global\n npx continuous-improvement uninstall --codex\n`);
48
- process.exit(code);
49
- }
50
-
51
- function exists(filePath) {
52
- return fs.existsSync(filePath);
53
- }
54
-
55
- function ensureDir(dirPath) {
56
- if (dryRun) return;
57
- fs.mkdirSync(dirPath, { recursive: true });
58
- }
59
-
60
- function readUtf8(filePath) {
61
- return fs.readFileSync(filePath, 'utf8');
62
- }
63
-
64
- function writeUtf8(filePath, content) {
65
- if (dryRun) return;
66
- ensureDir(path.dirname(filePath));
67
- fs.writeFileSync(filePath, content, 'utf8');
68
- }
69
-
70
- function appendBlock(filePath, block) {
71
- const trimmedBlock = block.trim();
72
- const existing = exists(filePath) ? readUtf8(filePath) : '';
73
-
74
- if (existing.includes(trimmedBlock)) {
75
- return { changed: false, reason: 'already-installed' };
76
- }
77
-
78
- const next = existing.trim().length === 0
79
- ? `${trimmedBlock}\n`
80
- : `${existing.replace(/\s*$/, '')}\n\n${trimmedBlock}\n`;
81
-
82
- writeUtf8(filePath, next);
83
- return { changed: true };
84
- }
85
-
86
- function removeBlock(filePath, block) {
87
- if (!exists(filePath)) {
88
- return { changed: false, reason: 'not-found' };
89
- }
90
-
91
- const trimmedBlock = block.trim();
92
- const existing = readUtf8(filePath);
93
-
94
- if (!existing.includes(trimmedBlock)) {
95
- return { changed: false, reason: 'not-installed' };
96
- }
97
-
98
- const next = existing
99
- .replace(new RegExp(`\\n?\\n?${escapeRegExp(trimmedBlock)}\\n?`, 'm'), '\n')
100
- .replace(/^\s+|\s+$/g, '');
101
-
102
- writeUtf8(filePath, next ? `${next}\n` : '');
103
- return { changed: true };
104
- }
105
-
106
- function escapeRegExp(value) {
107
- return value.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
108
- }
109
-
110
- function copySkill() {
111
- const sourceDir = path.join(rootDir, 'skills', 'continuous-improvement');
112
- const destDir = path.join(homeDir, '.openclaw', 'skills', 'continuous-improvement');
113
- const sourceFile = path.join(sourceDir, 'SKILL.md');
114
- const destFile = path.join(destDir, 'SKILL.md');
115
- const content = readUtf8(sourceFile);
116
-
117
- if (exists(destFile) && readUtf8(destFile) === content) {
118
- return { target: 'openclaw', location: destFile, changed: false, reason: 'already-installed' };
119
- }
120
-
121
- writeUtf8(destFile, content);
122
- return { target: 'openclaw', location: destFile, changed: true };
123
- }
124
-
125
- function setupMulahazah() {
126
- const mulahazahDir = path.join(homeDir, '.claude', 'mulahazah');
127
- const instinctsPersonalDir = path.join(mulahazahDir, 'instincts', 'personal');
128
- const projectsDir = path.join(mulahazahDir, 'projects');
129
-
130
- ensureDir(mulahazahDir);
131
- ensureDir(instinctsPersonalDir);
132
- ensureDir(projectsDir);
133
-
134
- const configDest = path.join(mulahazahDir, 'config.json');
135
- if (!exists(configDest)) {
136
- const configSrc = path.join(rootDir, 'config.json');
137
- if (exists(configSrc)) {
138
- writeUtf8(configDest, readUtf8(configSrc));
139
- }
140
- }
141
-
142
- const projectsRegistry = path.join(mulahazahDir, 'projects.json');
143
- if (!exists(projectsRegistry)) {
144
- writeUtf8(projectsRegistry, JSON.stringify({}, null, 2) + '\n');
145
- }
146
-
147
- return { location: mulahazahDir, changed: true };
148
- }
149
-
150
- function installHooks() {
151
- const mulahazahDir = path.join(homeDir, '.claude', 'mulahazah');
152
- const hookDest = path.join(mulahazahDir, 'observe.sh');
153
- const hookSrc = path.join(rootDir, 'hooks', 'observe.sh');
154
-
155
- ensureDir(mulahazahDir);
156
-
157
- if (exists(hookSrc)) {
158
- writeUtf8(hookDest, readUtf8(hookSrc));
159
- if (!dryRun) {
160
- fs.chmodSync(hookDest, 0o755);
161
- }
162
- }
163
-
164
- const settingsPath = path.join(homeDir, '.claude', 'settings.json');
165
- let settings = {};
166
- if (exists(settingsPath)) {
167
- try {
168
- settings = JSON.parse(readUtf8(settingsPath));
169
- } catch (_) {
170
- settings = {};
171
- }
172
- }
173
-
174
- const hookEntry = { matcher: '*', hooks: [{ type: 'command', command: hookDest }] };
175
-
176
- let changed = false;
177
-
178
- for (const hookType of ['PreToolUse', 'PostToolUse']) {
179
- if (!settings.hooks) settings.hooks = {};
180
- if (!settings.hooks[hookType]) settings.hooks[hookType] = [];
181
-
182
- const alreadyInstalled = settings.hooks[hookType].some(
183
- (entry) => entry.hooks && entry.hooks.some((h) => h.command === hookDest)
184
- );
185
-
186
- if (!alreadyInstalled) {
187
- settings.hooks[hookType].push(hookEntry);
188
- changed = true;
189
- }
190
- }
191
-
192
- if (changed) {
193
- writeUtf8(settingsPath, JSON.stringify(settings, null, 2) + '\n');
194
- }
195
-
196
- return { location: settingsPath, changed };
197
- }
198
-
199
- function copyObserverFiles() {
200
- const agentsSrc = path.join(rootDir, 'agents');
201
- const agentsDest = path.join(homeDir, '.claude', 'mulahazah', 'agents');
202
-
203
- ensureDir(agentsDest);
204
-
205
- const filesToCopy = ['observer.md', 'observer-loop.sh', 'start-observer.sh'];
206
- let changed = false;
207
-
208
- for (const fileName of filesToCopy) {
209
- const srcFile = path.join(agentsSrc, fileName);
210
- const destFile = path.join(agentsDest, fileName);
211
-
212
- if (exists(srcFile)) {
213
- const content = readUtf8(srcFile);
214
- const existingContent = exists(destFile) ? readUtf8(destFile) : null;
215
- if (existingContent !== content) {
216
- writeUtf8(destFile, content);
217
- if (!dryRun && fileName.endsWith('.sh')) {
218
- fs.chmodSync(destFile, 0o755);
219
- }
220
- changed = true;
221
- }
222
- }
223
- }
224
-
225
- return { location: agentsDest, changed };
226
- }
227
-
228
- function uninstallHooks() {
229
- const settingsPath = path.join(homeDir, '.claude', 'settings.json');
230
- if (!exists(settingsPath)) return;
231
-
232
- let settings;
233
- try {
234
- settings = JSON.parse(readUtf8(settingsPath));
235
- } catch (_) {
236
- return;
237
- }
238
-
239
- if (!settings.hooks) return;
240
-
241
- const mulahazahDir = path.join(homeDir, '.claude', 'mulahazah');
242
- const hookDest = path.join(mulahazahDir, 'observe.sh');
243
-
244
- let changed = false;
245
- for (const hookType of ['PreToolUse', 'PostToolUse']) {
246
- if (!Array.isArray(settings.hooks[hookType])) continue;
247
- const before = settings.hooks[hookType].length;
248
- settings.hooks[hookType] = settings.hooks[hookType].filter(
249
- (entry) => !(entry.hooks && entry.hooks.some((h) => h.command === hookDest))
250
- );
251
- if (settings.hooks[hookType].length === 0) {
252
- delete settings.hooks[hookType];
253
- }
254
- if (settings.hooks[hookType] === undefined || settings.hooks[hookType].length !== before) {
255
- changed = true;
256
- }
257
- }
258
-
259
- if (Object.keys(settings.hooks).length === 0) {
260
- delete settings.hooks;
261
- }
262
-
263
- if (changed) {
264
- writeUtf8(settingsPath, JSON.stringify(settings, null, 2) + '\n');
265
- }
266
- }
267
-
268
- function installClaude(globalInstall = useGlobal) {
269
- const filePath = globalInstall
270
- ? path.join(homeDir, '.claude', 'CLAUDE.md')
271
- : path.join(cwd, 'CLAUDE.md');
272
- const result = appendBlock(filePath, CODING_AGENT_BLOCK);
273
- return { target: 'claude', location: filePath, ...result };
274
- }
275
-
276
- function installCodex() {
277
- const filePath = path.join(cwd, 'AGENTS.md');
278
- const result = appendBlock(filePath, CODING_AGENT_BLOCK);
279
- return { target: 'codex', location: filePath, ...result };
280
- }
281
-
282
- function installCursor() {
283
- const filePath = path.join(cwd, '.cursorrules');
284
- const result = appendBlock(filePath, CURSOR_BLOCK);
285
- return { target: 'cursor', location: filePath, ...result };
286
- }
287
-
288
- function installChatgpt() {
289
- return { target: 'chatgpt', location: 'stdout', changed: true, printed: CHATGPT_BLOCK };
290
- }
291
-
292
- function uninstallClaude(globalInstall = useGlobal) {
293
- const filePath = globalInstall
294
- ? path.join(homeDir, '.claude', 'CLAUDE.md')
295
- : path.join(cwd, 'CLAUDE.md');
296
- const result = removeBlock(filePath, CODING_AGENT_BLOCK);
297
- return { target: 'claude', location: filePath, ...result };
298
- }
299
-
300
- function uninstallCodex() {
301
- const filePath = path.join(cwd, 'AGENTS.md');
302
- const result = removeBlock(filePath, CODING_AGENT_BLOCK);
303
- return { target: 'codex', location: filePath, ...result };
304
- }
305
-
306
- function uninstallCursor() {
307
- const filePath = path.join(cwd, '.cursorrules');
308
- const result = removeBlock(filePath, CURSOR_BLOCK);
309
- return { target: 'cursor', location: filePath, ...result };
310
- }
311
-
312
- function uninstallOpenclaw() {
313
- const destFile = path.join(homeDir, '.openclaw', 'skills', 'continuous-improvement', 'SKILL.md');
314
- if (!exists(destFile)) {
315
- return { target: 'openclaw', location: destFile, changed: false, reason: 'not-installed' };
316
- }
317
- if (!dryRun) {
318
- fs.rmSync(path.dirname(destFile), { recursive: true, force: true });
319
- }
320
- return { target: 'openclaw', location: destFile, changed: true };
321
- }
322
-
323
- function detectTargets() {
324
- const targets = [];
325
- if (exists(path.join(cwd, 'CLAUDE.md'))) targets.push('claude');
326
- if (exists(path.join(cwd, 'AGENTS.md'))) targets.push('codex');
327
- if (exists(path.join(cwd, '.cursorrules'))) targets.push('cursor');
328
- if (exists(path.join(homeDir, '.openclaw'))) targets.push('openclaw');
329
- if (targets.length === 0) {
330
- if (exists(path.join(homeDir, '.claude'))) targets.push('claude-global');
331
- }
332
- return targets;
333
- }
334
-
335
- function installTarget(target) {
336
- switch (target) {
337
- case 'claude': {
338
- const claudeResult = installClaude(false);
339
- const mulahazahResult = setupMulahazah();
340
- const hooksResult = installHooks();
341
- const observerResult = copyObserverFiles();
342
- return { ...claudeResult, mulahazah: mulahazahResult, hooks: hooksResult, observer: observerResult };
343
- }
344
- case 'claude-global': {
345
- const claudeResult = installClaude(true);
346
- const mulahazahResult = setupMulahazah();
347
- const hooksResult = installHooks();
348
- const observerResult = copyObserverFiles();
349
- return { ...claudeResult, mulahazah: mulahazahResult, hooks: hooksResult, observer: observerResult };
350
- }
351
- case 'codex':
352
- return installCodex();
353
- case 'cursor':
354
- return installCursor();
355
- case 'openclaw':
356
- return copySkill();
357
- case 'chatgpt':
358
- return installChatgpt();
359
- default:
360
- throw new Error(`Unknown target: ${target}`);
361
- }
362
- }
363
-
364
- function uninstallTarget(target) {
365
- switch (target) {
366
- case 'claude':
367
- uninstallHooks();
368
- return uninstallClaude(false);
369
- case 'claude-global':
370
- uninstallHooks();
371
- return uninstallClaude(true);
372
- case 'codex':
373
- return uninstallCodex();
374
- case 'cursor':
375
- return uninstallCursor();
376
- case 'openclaw':
377
- return uninstallOpenclaw();
378
- default:
379
- throw new Error(`Unknown target for uninstall: ${target}`);
380
- }
381
- }
382
-
383
- if (!command || command === '--help' || command === '-h' || flags.has('--help') || flags.has('-h')) {
384
- usage(0);
385
- }
386
-
387
- if (command !== 'install' && command !== 'uninstall') {
388
- console.error(`Unknown command: ${command}`);
389
- usage(1);
390
- }
391
-
392
- const targets = selectedTarget ? [selectedTarget] : detectTargets();
393
-
394
- if (targets.length === 0) {
395
- console.log('No target detected automatically.');
396
- console.log('Try one of:');
397
- console.log(' npx continuous-improvement install --claude');
398
- console.log(' npx continuous-improvement install --codex');
399
- console.log(' npx continuous-improvement install --cursor');
400
- console.log(' npx continuous-improvement install --openclaw');
401
- console.log(' npx continuous-improvement install --chatgpt');
402
- process.exit(0);
403
- }
404
-
405
- const results = command === 'install'
406
- ? targets.map(installTarget)
407
- : targets.filter((target) => target !== 'chatgpt').map(uninstallTarget);
408
-
409
- console.log(`continuous-improvement ${command}\n`);
410
- for (const result of results) {
411
- if (result.printed) {
412
- console.log(`✓ ${result.target}: copy this into ChatGPT Custom Instructions\n`);
413
- console.log(result.printed);
414
- continue;
415
- }
416
-
417
- const status = command === 'install'
418
- ? (result.changed ? 'installed' : (result.reason || 'unchanged'))
419
- : (result.changed ? 'removed' : (result.reason || 'unchanged'));
420
- console.log(`✓ ${result.target}: ${status} → ${result.location}${dryRun ? ' (dry-run)' : ''}`);
421
-
422
- if (command === 'install' && result.mulahazah) {
423
- console.log(` ✓ mulahazah: directory created → ~/.claude/mulahazah/`);
424
- }
425
- if (command === 'install' && result.hooks) {
426
- console.log(` ✓ hooks: PreToolUse + PostToolUse → ~/.claude/settings.json`);
427
- }
428
- if (command === 'install' && result.observer) {
429
- console.log(` ✓ observer: agent files copied → ~/.claude/mulahazah/agents/`);
430
- console.log(` To start background observer: ~/.claude/mulahazah/agents/start-observer.sh`);
431
- console.log(` Run /continuous-improvement after your next session to see what was learned.`);
432
- }
433
- }