cognitive-modules-cli 2.2.1 → 2.2.7

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 (101) hide show
  1. package/CHANGELOG.md +11 -0
  2. package/LICENSE +21 -0
  3. package/README.md +35 -29
  4. package/dist/cli.js +519 -23
  5. package/dist/commands/add.d.ts +33 -14
  6. package/dist/commands/add.js +383 -16
  7. package/dist/commands/compose.js +60 -23
  8. package/dist/commands/index.d.ts +4 -0
  9. package/dist/commands/index.js +4 -0
  10. package/dist/commands/init.js +23 -1
  11. package/dist/commands/migrate.d.ts +30 -0
  12. package/dist/commands/migrate.js +650 -0
  13. package/dist/commands/pipe.d.ts +1 -0
  14. package/dist/commands/pipe.js +31 -11
  15. package/dist/commands/remove.js +33 -2
  16. package/dist/commands/run.d.ts +2 -0
  17. package/dist/commands/run.js +61 -28
  18. package/dist/commands/search.d.ts +28 -0
  19. package/dist/commands/search.js +143 -0
  20. package/dist/commands/test.d.ts +65 -0
  21. package/dist/commands/test.js +454 -0
  22. package/dist/commands/update.d.ts +1 -0
  23. package/dist/commands/update.js +106 -14
  24. package/dist/commands/validate.d.ts +36 -0
  25. package/dist/commands/validate.js +97 -0
  26. package/dist/errors/index.d.ts +225 -0
  27. package/dist/errors/index.js +420 -0
  28. package/dist/mcp/server.js +84 -79
  29. package/dist/modules/composition.js +97 -32
  30. package/dist/modules/loader.js +4 -2
  31. package/dist/modules/runner.d.ts +72 -5
  32. package/dist/modules/runner.js +306 -59
  33. package/dist/modules/subagent.d.ts +6 -1
  34. package/dist/modules/subagent.js +18 -13
  35. package/dist/modules/validator.js +14 -6
  36. package/dist/providers/anthropic.d.ts +15 -0
  37. package/dist/providers/anthropic.js +147 -5
  38. package/dist/providers/base.d.ts +11 -0
  39. package/dist/providers/base.js +18 -0
  40. package/dist/providers/gemini.d.ts +15 -0
  41. package/dist/providers/gemini.js +122 -5
  42. package/dist/providers/ollama.d.ts +15 -0
  43. package/dist/providers/ollama.js +111 -3
  44. package/dist/providers/openai.d.ts +11 -0
  45. package/dist/providers/openai.js +133 -0
  46. package/dist/registry/client.d.ts +212 -0
  47. package/dist/registry/client.js +359 -0
  48. package/dist/registry/index.d.ts +4 -0
  49. package/dist/registry/index.js +4 -0
  50. package/dist/registry/tar.d.ts +8 -0
  51. package/dist/registry/tar.js +353 -0
  52. package/dist/server/http.js +301 -45
  53. package/dist/server/index.d.ts +2 -0
  54. package/dist/server/index.js +1 -0
  55. package/dist/server/sse.d.ts +13 -0
  56. package/dist/server/sse.js +22 -0
  57. package/dist/types.d.ts +32 -1
  58. package/dist/types.js +4 -1
  59. package/dist/version.d.ts +1 -0
  60. package/dist/version.js +4 -0
  61. package/package.json +31 -7
  62. package/dist/modules/composition.test.d.ts +0 -11
  63. package/dist/modules/composition.test.js +0 -450
  64. package/dist/modules/policy.test.d.ts +0 -10
  65. package/dist/modules/policy.test.js +0 -369
  66. package/src/cli.ts +0 -471
  67. package/src/commands/add.ts +0 -315
  68. package/src/commands/compose.ts +0 -185
  69. package/src/commands/index.ts +0 -13
  70. package/src/commands/init.ts +0 -94
  71. package/src/commands/list.ts +0 -33
  72. package/src/commands/pipe.ts +0 -76
  73. package/src/commands/remove.ts +0 -57
  74. package/src/commands/run.ts +0 -80
  75. package/src/commands/update.ts +0 -130
  76. package/src/commands/versions.ts +0 -79
  77. package/src/index.ts +0 -90
  78. package/src/mcp/index.ts +0 -5
  79. package/src/mcp/server.ts +0 -403
  80. package/src/modules/composition.test.ts +0 -558
  81. package/src/modules/composition.ts +0 -1674
  82. package/src/modules/index.ts +0 -9
  83. package/src/modules/loader.ts +0 -508
  84. package/src/modules/policy.test.ts +0 -455
  85. package/src/modules/runner.ts +0 -1983
  86. package/src/modules/subagent.ts +0 -277
  87. package/src/modules/validator.ts +0 -700
  88. package/src/providers/anthropic.ts +0 -89
  89. package/src/providers/base.ts +0 -29
  90. package/src/providers/deepseek.ts +0 -83
  91. package/src/providers/gemini.ts +0 -117
  92. package/src/providers/index.ts +0 -78
  93. package/src/providers/minimax.ts +0 -81
  94. package/src/providers/moonshot.ts +0 -82
  95. package/src/providers/ollama.ts +0 -83
  96. package/src/providers/openai.ts +0 -84
  97. package/src/providers/qwen.ts +0 -82
  98. package/src/server/http.ts +0 -316
  99. package/src/server/index.ts +0 -6
  100. package/src/types.ts +0 -599
  101. package/tsconfig.json +0 -17
package/dist/cli.js CHANGED
@@ -15,8 +15,9 @@
15
15
  */
16
16
  import { parseArgs } from 'node:util';
17
17
  import { getProvider, listProviders } from './providers/index.js';
18
- import { run, list, pipe, init, add, update, remove, versions, compose, composeInfo } from './commands/index.js';
19
- const VERSION = '1.3.0';
18
+ import { run, list, pipe, init, add, update, remove, versions, compose, composeInfo, validate, validateAll, migrate, migrateAll, test, testAll, search, listCategories, info } from './commands/index.js';
19
+ import { listModules, getDefaultSearchPaths } from './modules/loader.js';
20
+ import { VERSION } from './version.js';
20
21
  async function main() {
21
22
  const args = process.argv.slice(2);
22
23
  const command = args[0];
@@ -29,7 +30,7 @@ async function main() {
29
30
  process.exit(0);
30
31
  }
31
32
  // Parse common options
32
- const { values } = parseArgs({
33
+ const { values, positionals } = parseArgs({
33
34
  args: args.slice(1),
34
35
  options: {
35
36
  args: { type: 'string', short: 'a' },
@@ -40,6 +41,7 @@ async function main() {
40
41
  pretty: { type: 'boolean', default: false },
41
42
  verbose: { type: 'boolean', short: 'V', default: false },
42
43
  'no-validate': { type: 'boolean', default: false },
44
+ stream: { type: 'boolean', default: false },
43
45
  // Add/update options
44
46
  name: { type: 'string', short: 'n' },
45
47
  tag: { type: 'string', short: 't' },
@@ -52,6 +54,14 @@ async function main() {
52
54
  'max-depth': { type: 'string', short: 'd' },
53
55
  timeout: { type: 'string', short: 'T' },
54
56
  trace: { type: 'boolean', default: false },
57
+ // Validate/migrate options
58
+ v22: { type: 'boolean', default: false },
59
+ 'dry-run': { type: 'boolean', default: false },
60
+ 'no-backup': { type: 'boolean', default: false },
61
+ all: { type: 'boolean', default: false },
62
+ format: { type: 'string', short: 'f' },
63
+ // Search options
64
+ category: { type: 'string', short: 'c' },
55
65
  },
56
66
  allowPositionals: true,
57
67
  });
@@ -83,12 +93,21 @@ async function main() {
83
93
  noValidate: values['no-validate'],
84
94
  pretty: values.pretty,
85
95
  verbose: values.verbose,
96
+ stream: values.stream,
86
97
  });
87
98
  if (!result.success) {
88
- console.error(`Error: ${result.error}`);
99
+ if (result.data) {
100
+ console.log(JSON.stringify(result.data, null, values.pretty ? 2 : 0));
101
+ }
102
+ else {
103
+ console.error(`Error: ${result.error}`);
104
+ }
89
105
  process.exit(1);
90
106
  }
91
- console.log(JSON.stringify(result.data, null, values.pretty ? 2 : 0));
107
+ // Stream mode prints events as NDJSON already.
108
+ if (!values.stream) {
109
+ console.log(JSON.stringify(result.data, null, values.pretty ? 2 : 0));
110
+ }
92
111
  break;
93
112
  }
94
113
  case 'list': {
@@ -144,33 +163,137 @@ async function main() {
144
163
  break;
145
164
  }
146
165
  case 'doctor': {
147
- console.log('Cognitive Runtime - Environment Check\n');
148
- console.log('Providers:');
149
- for (const p of listProviders()) {
150
- const status = p.configured ? '✓ configured' : '– not configured';
151
- console.log(` ${p.name}: ${status} (${p.model})`);
166
+ console.log('═══════════════════════════════════════════════════════════');
167
+ console.log(`Cognitive Runtime v${VERSION} - Environment Diagnostics`);
168
+ console.log('═══════════════════════════════════════════════════════════\n');
169
+ // 1. Version info
170
+ console.log('Version Information:');
171
+ console.log(` Runtime: v${VERSION}`);
172
+ console.log(` Spec: v2.2`);
173
+ console.log('');
174
+ // 2. Provider configuration
175
+ console.log('LLM Providers:');
176
+ const providers = listProviders();
177
+ let hasConfiguredProvider = false;
178
+ for (const p of providers) {
179
+ const status = p.configured ? '✓' : '–';
180
+ const apiKeyStatus = p.configured ? 'API key set' : 'not configured';
181
+ console.log(` ${status} ${p.name}`);
182
+ console.log(` Model: ${p.model}`);
183
+ console.log(` Status: ${apiKeyStatus}`);
184
+ if (p.configured)
185
+ hasConfiguredProvider = true;
152
186
  }
153
187
  console.log('');
188
+ // 3. Active provider
189
+ console.log('Active Provider:');
154
190
  try {
155
191
  const provider = getProvider();
156
- console.log(`Active provider: ${provider.name}`);
192
+ console.log(` ${provider.name} (ready to use)`);
193
+ }
194
+ catch {
195
+ console.log(' ✗ None configured');
196
+ console.log(' → Set one of: OPENAI_API_KEY, ANTHROPIC_API_KEY, GEMINI_API_KEY, etc.');
197
+ }
198
+ console.log('');
199
+ // 4. Module scan
200
+ console.log('Module Search Paths:');
201
+ const searchPaths = getDefaultSearchPaths(ctx.cwd);
202
+ for (const p of searchPaths) {
203
+ console.log(` • ${p}`);
204
+ }
205
+ console.log('');
206
+ // 5. Installed modules
207
+ console.log('Installed Modules:');
208
+ try {
209
+ const modules = await listModules(searchPaths);
210
+ if (modules.length === 0) {
211
+ console.log(' – No modules found');
212
+ console.log(' → Use `cog add <repo> -m <module>` to install modules');
213
+ }
214
+ else {
215
+ let v22Count = 0;
216
+ let legacyCount = 0;
217
+ for (const m of modules) {
218
+ const isV22 = m.tier !== undefined || m.formatVersion === 'v2.2';
219
+ if (isV22)
220
+ v22Count++;
221
+ else
222
+ legacyCount++;
223
+ const versionBadge = isV22 ? '[v2.2]' : '[legacy]';
224
+ const tierBadge = m.tier ? `tier:${m.tier}` : '';
225
+ console.log(` ✓ ${m.name} ${versionBadge} ${tierBadge}`);
226
+ console.log(` ${m.responsibility || 'No description'}`);
227
+ }
228
+ console.log('');
229
+ console.log(` Total: ${modules.length} modules (${v22Count} v2.2, ${legacyCount} legacy)`);
230
+ if (legacyCount > 0) {
231
+ console.log('');
232
+ console.log(' ⚠ Legacy modules detected');
233
+ console.log(' → Use `cog migrate --all` to upgrade to v2.2');
234
+ }
235
+ }
236
+ }
237
+ catch (e) {
238
+ console.log(` ✗ Error scanning modules: ${e instanceof Error ? e.message : e}`);
239
+ }
240
+ console.log('');
241
+ // 6. Recommendations
242
+ console.log('Recommendations:');
243
+ const recommendations = [];
244
+ if (!hasConfiguredProvider) {
245
+ recommendations.push('Configure at least one LLM provider (e.g., OPENAI_API_KEY)');
246
+ }
247
+ try {
248
+ const modules = await listModules(searchPaths);
249
+ if (modules.length === 0) {
250
+ recommendations.push('Install some modules with `cog add`');
251
+ }
252
+ // Check for modules without tests
253
+ let modulesWithoutTests = 0;
254
+ for (const m of modules) {
255
+ const testsConfig = m.tests;
256
+ if (!testsConfig || testsConfig.length === 0) {
257
+ modulesWithoutTests++;
258
+ }
259
+ }
260
+ if (modulesWithoutTests > 0) {
261
+ recommendations.push(`${modulesWithoutTests} module(s) have no tests - consider adding golden tests`);
262
+ }
157
263
  }
158
264
  catch {
159
- console.log('Active provider: none (set an API key)');
265
+ // Ignore
266
+ }
267
+ if (recommendations.length === 0) {
268
+ console.log(' ✓ All good! Your environment is properly configured.');
269
+ }
270
+ else {
271
+ for (const rec of recommendations) {
272
+ console.log(` → ${rec}`);
273
+ }
160
274
  }
275
+ console.log('');
276
+ console.log('───────────────────────────────────────────────────────────');
277
+ console.log('For more help: cog --help');
161
278
  break;
162
279
  }
163
280
  case 'add': {
164
281
  const url = args[1];
165
282
  if (!url || url.startsWith('-')) {
166
- console.error('Usage: cog add <url> [--module <name>] [--tag <version>]');
283
+ console.error('Usage: cog add <source> [--module <name>] [--tag <version>]');
284
+ console.error('');
285
+ console.error('Source can be:');
286
+ console.error(' - GitHub: org/repo (e.g., ziel-io/cognitive-modules)');
287
+ console.error(' - Registry: module-name[@version] (e.g., code-simplifier)');
167
288
  console.error('');
168
289
  console.error('Examples:');
290
+ console.error(' cog add code-simplifier # From registry');
291
+ console.error(' cog add code-reviewer@1.2.0 # Specific version');
169
292
  console.error(' cog add ziel-io/cognitive-modules -m code-simplifier');
170
293
  console.error(' cog add org/repo --module my-module --tag v1.0.0');
171
294
  process.exit(1);
172
295
  }
173
- console.log(`→ Adding module from: ${url}`);
296
+ console.log(`→ Adding module: ${url}`);
174
297
  if (values.module)
175
298
  console.log(` Module path: ${values.module}`);
176
299
  if (values.tag)
@@ -272,9 +395,11 @@ async function main() {
272
395
  verbose: values.verbose,
273
396
  });
274
397
  if (!result.success) {
275
- console.error(`Error: ${result.error}`);
276
398
  if (result.data) {
277
- console.error('Partial results:', JSON.stringify(result.data, null, 2));
399
+ console.log(JSON.stringify(result.data, null, values.pretty ? 2 : 0));
400
+ }
401
+ else {
402
+ console.error(`Error: ${result.error}`);
278
403
  }
279
404
  process.exit(1);
280
405
  }
@@ -318,6 +443,345 @@ async function main() {
318
443
  }
319
444
  break;
320
445
  }
446
+ case 'validate': {
447
+ const target = args[1];
448
+ if (values.all) {
449
+ // Validate all modules
450
+ console.log('→ Validating all modules...\n');
451
+ const result = await validateAll(ctx, {
452
+ v22: values.v22,
453
+ format: values.format || 'text',
454
+ });
455
+ const data = result.data;
456
+ if (values.format === 'json') {
457
+ console.log(JSON.stringify(data, null, 2));
458
+ }
459
+ else {
460
+ console.log(`Total: ${data.total}, Valid: ${data.valid}, Invalid: ${data.invalid}\n`);
461
+ for (const r of data.results) {
462
+ const status = r.valid ? '✓' : '✗';
463
+ console.log(`${status} ${r.moduleName || 'unknown'}`);
464
+ for (const err of r.errors) {
465
+ console.log(` Error: ${err}`);
466
+ }
467
+ for (const warn of r.warnings) {
468
+ console.log(` Warning: ${warn}`);
469
+ }
470
+ }
471
+ }
472
+ process.exit(result.success ? 0 : 1);
473
+ }
474
+ if (!target || target.startsWith('-')) {
475
+ console.error('Usage: cog validate <module> [--v22] [--all]');
476
+ process.exit(1);
477
+ }
478
+ console.log(`→ Validating module: ${target}`);
479
+ if (values.v22)
480
+ console.log(' Using strict v2.2 validation');
481
+ console.log('');
482
+ const result = await validate(target, ctx, {
483
+ v22: values.v22,
484
+ format: values.format || 'text',
485
+ });
486
+ const data = result.data;
487
+ if (values.format === 'json') {
488
+ console.log(JSON.stringify(data, null, 2));
489
+ }
490
+ else {
491
+ if (data.valid) {
492
+ console.log('✓ Module is valid');
493
+ }
494
+ else {
495
+ console.log('✗ Validation failed');
496
+ console.log('');
497
+ for (const err of data.errors) {
498
+ console.log(` Error: ${err}`);
499
+ }
500
+ }
501
+ if (data.warnings.length > 0) {
502
+ console.log('');
503
+ console.log('Warnings:');
504
+ for (const warn of data.warnings) {
505
+ console.log(` ${warn}`);
506
+ }
507
+ }
508
+ }
509
+ process.exit(result.success ? 0 : 1);
510
+ }
511
+ case 'migrate': {
512
+ const target = args[1];
513
+ const dryRun = values['dry-run'];
514
+ const backup = !values['no-backup'];
515
+ if (values.all) {
516
+ // Migrate all modules
517
+ console.log('→ Migrating all modules to v2.2...');
518
+ if (dryRun)
519
+ console.log(' (Dry run - no changes will be made)');
520
+ console.log('');
521
+ const result = await migrateAll(ctx, { dryRun, backup });
522
+ const data = result.data;
523
+ console.log(`Total: ${data.total}, Migrated: ${data.migrated}, Skipped: ${data.skipped}, Failed: ${data.failed}\n`);
524
+ for (const r of data.results) {
525
+ const status = r.success ? (r.changes.length > 0 ? '✓' : '–') : '✗';
526
+ console.log(`${status} ${r.moduleName}`);
527
+ for (const change of r.changes) {
528
+ console.log(` ${change}`);
529
+ }
530
+ for (const warn of r.warnings) {
531
+ console.log(` Warning: ${warn}`);
532
+ }
533
+ }
534
+ process.exit(result.success ? 0 : 1);
535
+ }
536
+ if (!target || target.startsWith('-')) {
537
+ console.error('Usage: cog migrate <module> [--dry-run] [--no-backup] [--all]');
538
+ process.exit(1);
539
+ }
540
+ console.log(`→ Migrating module to v2.2: ${target}`);
541
+ if (dryRun)
542
+ console.log(' (Dry run - no changes will be made)');
543
+ console.log('');
544
+ const result = await migrate(target, ctx, { dryRun, backup });
545
+ const data = result.data;
546
+ if (data.success) {
547
+ if (data.changes.length > 0) {
548
+ console.log('✓ Migration completed');
549
+ console.log('');
550
+ for (const change of data.changes) {
551
+ console.log(` ${change}`);
552
+ }
553
+ }
554
+ else {
555
+ console.log('– No changes needed');
556
+ }
557
+ }
558
+ else {
559
+ console.log('✗ Migration failed');
560
+ }
561
+ if (data.warnings.length > 0) {
562
+ console.log('');
563
+ console.log('Warnings:');
564
+ for (const warn of data.warnings) {
565
+ console.log(` ${warn}`);
566
+ }
567
+ }
568
+ process.exit(result.success ? 0 : 1);
569
+ }
570
+ case 'test': {
571
+ const target = args[1];
572
+ if (values.all) {
573
+ // Test all modules
574
+ console.log('→ Running tests for all modules...\n');
575
+ const result = await testAll(ctx, {
576
+ verbose: values.verbose,
577
+ timeout: values.timeout ? parseInt(values.timeout, 10) : undefined,
578
+ });
579
+ const data = result.data;
580
+ // Summary
581
+ console.log('═══════════════════════════════════════════════════════════');
582
+ console.log('Test Summary');
583
+ console.log('═══════════════════════════════════════════════════════════');
584
+ console.log(`Total: ${data.total}, Passed: ${data.passed}, Failed: ${data.failed}, Skipped: ${data.skipped}`);
585
+ console.log(`Duration: ${data.duration_ms}ms\n`);
586
+ // Per-module results
587
+ for (const m of data.modules) {
588
+ if (m.total === 0) {
589
+ console.log(`– ${m.moduleName}: no tests`);
590
+ continue;
591
+ }
592
+ const status = m.failed === 0 ? '✓' : '✗';
593
+ console.log(`${status} ${m.moduleName}: ${m.passed}/${m.total} passed`);
594
+ for (const r of m.results) {
595
+ if (!r.passed) {
596
+ console.log(` ✗ ${r.name}: ${r.error}`);
597
+ }
598
+ }
599
+ }
600
+ process.exit(result.success ? 0 : 1);
601
+ }
602
+ if (!target || target.startsWith('-')) {
603
+ console.error('Usage: cog test <module> [--all] [--verbose] [--timeout <ms>]');
604
+ process.exit(1);
605
+ }
606
+ console.log(`→ Running tests for module: ${target}\n`);
607
+ const result = await test(target, ctx, {
608
+ verbose: values.verbose,
609
+ timeout: values.timeout ? parseInt(values.timeout, 10) : undefined,
610
+ });
611
+ if (!result.success && !result.data) {
612
+ console.error(`✗ ${result.error}`);
613
+ process.exit(1);
614
+ }
615
+ const data = result.data;
616
+ if (data.total === 0) {
617
+ console.log('– No tests found for this module');
618
+ console.log('');
619
+ console.log('To add tests, create a tests/ directory with:');
620
+ console.log(' - tests/case1.input.json');
621
+ console.log(' - tests/case1.expected.json');
622
+ console.log('');
623
+ console.log('Or define in module.yaml:');
624
+ console.log(' tests:');
625
+ console.log(' - tests/case1.input.json -> tests/case1.expected.json');
626
+ process.exit(0);
627
+ }
628
+ // Results
629
+ console.log(`Module: ${data.moduleName}`);
630
+ console.log(`Total: ${data.total}, Passed: ${data.passed}, Failed: ${data.failed}`);
631
+ console.log(`Duration: ${data.duration_ms}ms\n`);
632
+ for (const r of data.results) {
633
+ const status = r.passed ? '✓' : '✗';
634
+ console.log(`${status} ${r.name} (${r.duration_ms}ms)`);
635
+ if (!r.passed) {
636
+ if (r.error) {
637
+ console.log(` Error: ${r.error}`);
638
+ }
639
+ if (r.diff && r.diff.length > 0) {
640
+ console.log(' Differences:');
641
+ for (const d of r.diff.slice(0, 5)) {
642
+ console.log(` ${d.field}:`);
643
+ console.log(` expected: ${JSON.stringify(d.expected)}`);
644
+ console.log(` actual: ${JSON.stringify(d.actual)}`);
645
+ }
646
+ if (r.diff.length > 5) {
647
+ console.log(` ... and ${r.diff.length - 5} more`);
648
+ }
649
+ }
650
+ }
651
+ }
652
+ process.exit(result.success ? 0 : 1);
653
+ }
654
+ case 'search': {
655
+ // Use positionals for query (excludes options)
656
+ const query = positionals.join(' ');
657
+ const limit = values.limit ? parseInt(values.limit, 10) : 20;
658
+ const category = values.category;
659
+ const result = await search(query, ctx, { limit, category });
660
+ if (!result.success) {
661
+ console.error(`✗ ${result.error}`);
662
+ process.exit(1);
663
+ }
664
+ const data = result.data;
665
+ if (data.results.length === 0) {
666
+ if (query) {
667
+ console.log(`No modules found for: "${query}"`);
668
+ }
669
+ else {
670
+ console.log('No modules available in registry.');
671
+ }
672
+ console.log('');
673
+ console.log('Try:');
674
+ console.log(' cog search code review');
675
+ console.log(' cog search task management');
676
+ }
677
+ else {
678
+ if (query) {
679
+ console.log(`Search results for "${query}" (${data.total} total):\n`);
680
+ }
681
+ else {
682
+ console.log(`Available modules (${data.total} total):\n`);
683
+ }
684
+ for (const mod of data.results) {
685
+ console.log(` ${mod.name} (v${mod.version})`);
686
+ console.log(` ${mod.description}`);
687
+ if (mod.keywords.length > 0) {
688
+ console.log(` Tags: ${mod.keywords.join(', ')}`);
689
+ }
690
+ console.log('');
691
+ }
692
+ console.log('Install with:');
693
+ console.log(` cog add <module-name>`);
694
+ }
695
+ break;
696
+ }
697
+ case 'registry': {
698
+ // positionals[0] is the subcommand, positionals[1] is the argument
699
+ const subCommand = positionals[0];
700
+ if (!subCommand || subCommand === 'list') {
701
+ // List all modules
702
+ const result = await search('', ctx, {});
703
+ if (!result.success) {
704
+ console.error(`✗ ${result.error}`);
705
+ process.exit(1);
706
+ }
707
+ const data = result.data;
708
+ console.log(`Registry modules (${data.total} total):\n`);
709
+ for (const mod of data.results) {
710
+ console.log(` ${mod.name} (v${mod.version})`);
711
+ console.log(` ${mod.description}`);
712
+ console.log('');
713
+ }
714
+ }
715
+ else if (subCommand === 'categories') {
716
+ const result = await listCategories(ctx, {});
717
+ if (!result.success) {
718
+ console.error(`✗ ${result.error}`);
719
+ process.exit(1);
720
+ }
721
+ const data = result.data;
722
+ console.log('Registry categories:\n');
723
+ for (const cat of data.categories) {
724
+ console.log(` ${cat.key} - ${cat.name} (${cat.moduleCount} modules)`);
725
+ console.log(` ${cat.description}`);
726
+ console.log('');
727
+ }
728
+ }
729
+ else if (subCommand === 'info') {
730
+ // positionals[1] is the module name (positionals[0] is 'info')
731
+ const moduleName = positionals[1];
732
+ if (!moduleName) {
733
+ console.error('Usage: cog registry info <module>');
734
+ process.exit(1);
735
+ }
736
+ const result = await info(moduleName, ctx, {});
737
+ if (!result.success) {
738
+ console.error(`✗ ${result.error}`);
739
+ process.exit(1);
740
+ }
741
+ const data = result.data;
742
+ const mod = data.module;
743
+ console.log(`Module: ${mod.name}\n`);
744
+ console.log(` Version: ${mod.version}`);
745
+ console.log(` Description: ${mod.description}`);
746
+ console.log(` Author: ${mod.author}`);
747
+ console.log(` Source: ${mod.source}`);
748
+ if (mod.tier)
749
+ console.log(` Tier: ${mod.tier}`);
750
+ if (mod.license)
751
+ console.log(` License: ${mod.license}`);
752
+ if (mod.repository)
753
+ console.log(` Repository: ${mod.repository}`);
754
+ if (mod.keywords.length > 0)
755
+ console.log(` Keywords: ${mod.keywords.join(', ')}`);
756
+ if (mod.conformance_level)
757
+ console.log(` Conformance Level: ${mod.conformance_level}`);
758
+ if (mod.verified !== undefined)
759
+ console.log(` Verified: ${mod.verified ? 'Yes' : 'No'}`);
760
+ if (mod.deprecated)
761
+ console.log(` DEPRECATED: This module is deprecated`);
762
+ console.log('');
763
+ console.log('Install with:');
764
+ console.log(` cog add ${mod.name}`);
765
+ }
766
+ else if (subCommand === 'refresh') {
767
+ // Force refresh the registry cache
768
+ const { RegistryClient } = await import('./registry/client.js');
769
+ const client = new RegistryClient();
770
+ await client.fetchRegistry(true);
771
+ console.log('✓ Registry cache refreshed');
772
+ }
773
+ else {
774
+ console.error(`Unknown registry subcommand: ${subCommand}`);
775
+ console.error('');
776
+ console.error('Usage:');
777
+ console.error(' cog registry list List all modules');
778
+ console.error(' cog registry categories List categories');
779
+ console.error(' cog registry info <mod> Show module details');
780
+ console.error(' cog registry refresh Refresh cache');
781
+ process.exit(1);
782
+ }
783
+ break;
784
+ }
321
785
  default:
322
786
  console.error(`Unknown command: ${command}`);
323
787
  console.error('Run "cog --help" for usage.');
@@ -342,18 +806,23 @@ USAGE:
342
806
 
343
807
  COMMANDS:
344
808
  run <module> Run a Cognitive Module
809
+ test <module> Run golden tests for a module
345
810
  compose <module> Execute a composed module workflow
346
811
  compose-info <mod> Show composition configuration
347
- list List available modules
348
- add <url> Add module from GitHub
812
+ list List available (installed) modules
813
+ add <source> Add module from Registry or GitHub
349
814
  update <module> Update module to latest version
350
815
  remove <module> Remove installed module
351
816
  versions <url> List available versions
817
+ search [query] Search modules in registry
818
+ registry <cmd> Registry commands (list, categories, info, refresh)
819
+ validate <module> Validate module structure
820
+ migrate <module> Migrate module to v2.2 format
352
821
  pipe Pipe mode (stdin/stdout)
353
822
  init [name] Initialize project or create module
354
823
  serve Start HTTP API server
355
824
  mcp Start MCP server (for Claude Code, Cursor)
356
- doctor Check configuration
825
+ doctor Check environment and configuration
357
826
 
358
827
  OPTIONS:
359
828
  -a, --args <str> Arguments to pass to module
@@ -372,12 +841,28 @@ OPTIONS:
372
841
  -d, --max-depth <n> Max composition depth (default: 5)
373
842
  -T, --timeout <ms> Composition timeout in milliseconds
374
843
  --trace Include execution trace (for compose)
844
+ --v22 Use strict v2.2 validation (for validate)
845
+ --dry-run Show what would be done without changes (for migrate)
846
+ --no-backup Skip backup before migration (for migrate)
847
+ --all Process all modules (for validate/migrate)
848
+ -f, --format <fmt> Output format: text or json (for validate)
849
+ -c, --category <cat> Filter by category (for search)
850
+ -l, --limit <n> Limit results (for search, versions)
375
851
  -v, --version Show version
376
852
  -h, --help Show this help
377
853
 
378
854
  EXAMPLES:
379
- # Add modules from GitHub
380
- npx cognitive-modules-cli add ziel-io/cognitive-modules -m code-simplifier
855
+ # Search and discover modules
856
+ cog search code review # Search by keywords
857
+ cog search # List all available modules
858
+ cog search --category code-quality # Search within category
859
+ cog registry categories # View module categories
860
+ cog registry info code-simplifier # Module details
861
+
862
+ # Add modules from registry or GitHub
863
+ cog add code-simplifier # From registry
864
+ cog add code-reviewer@1.2.0 # Specific version from registry
865
+ cog add ziel-io/cognitive-modules -m code-simplifier # From GitHub
381
866
  cog add org/repo --module my-module --tag v1.0.0
382
867
 
383
868
  # Version management
@@ -385,6 +870,17 @@ EXAMPLES:
385
870
  cog versions ziel-io/cognitive-modules
386
871
  cog remove code-simplifier
387
872
 
873
+ # Validation, testing, and migration
874
+ cog validate code-reviewer
875
+ cog validate code-reviewer --v22
876
+ cog validate --all
877
+ cog test code-simplifier # Run golden tests
878
+ cog test code-simplifier --verbose # With detailed output
879
+ cog test --all # Test all modules
880
+ cog migrate code-reviewer --dry-run
881
+ cog migrate code-reviewer
882
+ cog migrate --all --no-backup
883
+
388
884
  # Run modules
389
885
  cog run code-reviewer --args "def foo(): pass"
390
886
  cog run code-reviewer --provider openai --model gpt-4o --args "..."
@@ -399,10 +895,10 @@ EXAMPLES:
399
895
  cog serve --port 8080
400
896
  cog mcp
401
897
 
402
- # Other
898
+ # Environment check
899
+ cog doctor # Full diagnostics
403
900
  echo "review this code" | cog pipe --module code-reviewer
404
901
  cog init my-module
405
- cog doctor
406
902
 
407
903
  ENVIRONMENT:
408
904
  GEMINI_API_KEY Google Gemini