codymaster 4.4.5 → 4.5.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.
Files changed (186) hide show
  1. package/CHANGELOG.md +33 -0
  2. package/README.md +29 -14
  3. package/commands/demo.md +1 -1
  4. package/dist/context-bus.js +70 -0
  5. package/dist/context-db.js +265 -0
  6. package/dist/continuity.js +12 -0
  7. package/dist/file-watcher.js +79 -0
  8. package/dist/index.js +152 -1
  9. package/dist/l0-indexer.js +158 -0
  10. package/dist/mcp-context-server.js +400 -0
  11. package/dist/migrate-json-to-sqlite.js +126 -0
  12. package/dist/skill-chain.js +19 -3
  13. package/dist/token-budget.js +108 -0
  14. package/dist/uri-resolver.js +203 -0
  15. package/package.json +4 -1
  16. package/skills/_shared/helpers.md +50 -14
  17. package/skills/cm-autopilot/SKILL.md +29 -0
  18. package/skills/cm-autopilot/scripts/autopilot.py +190 -0
  19. package/skills/cm-continuity/SKILL.md +90 -28
  20. package/skills/cm-skill-chain/SKILL.md +47 -1
  21. package/skills/cm-start/SKILL.md +11 -2
  22. package/skills/boxme-git-config/SKILL.md +0 -56
  23. package/skills/boxme-local-dev/SKILL.md +0 -66
  24. package/skills/jobs-to-be-done/SKILL.md +0 -266
  25. package/skills/jobs-to-be-done/references/case-studies.md +0 -154
  26. package/skills/jobs-to-be-done/references/competitive-strategy.md +0 -280
  27. package/skills/jobs-to-be-done/references/diagnostics.md +0 -158
  28. package/skills/jobs-to-be-done/references/innovation-process.md +0 -392
  29. package/skills/jobs-to-be-done/references/organizational-change.md +0 -328
  30. package/skills/marketplace-report-crawler/SKILL.md +0 -176
  31. package/skills/marketplace-report-crawler/config/accounts.json +0 -41
  32. package/skills/marketplace-report-crawler/config/report-types.json +0 -422
  33. package/skills/marketplace-report-crawler/config/sessions.json +0 -3
  34. package/skills/marketplace-report-crawler/scripts/ab-wrapper.sh +0 -102
  35. package/skills/marketplace-report-crawler/scripts/browser-actions/lazada/lazada-actions.js +0 -114
  36. package/skills/marketplace-report-crawler/scripts/browser-actions/shopee/shopee-actions.js +0 -94
  37. package/skills/marketplace-report-crawler/scripts/browser-actions/tiktok/tiktok-actions.js +0 -272
  38. package/skills/marketplace-report-crawler/scripts/crawl-runner.js +0 -281
  39. package/skills/marketplace-report-crawler/scripts/session-check.sh +0 -72
  40. package/skills/marketplace-report-crawler/scripts/session-manager.sh +0 -349
  41. package/skills/marketplace-report-crawler/scripts/setup-folders.sh +0 -83
  42. package/skills/medical-research/SKILL.md +0 -194
  43. package/skills/medical-research/scripts/evidence_checker.py +0 -288
  44. package/skills/mom-test/SKILL.md +0 -267
  45. package/skills/mom-test/references/avoiding-bad-data.md +0 -221
  46. package/skills/mom-test/references/case-studies.md +0 -306
  47. package/skills/mom-test/references/commitment-advancement.md +0 -219
  48. package/skills/mom-test/references/finding-conversations.md +0 -251
  49. package/skills/mom-test/references/processing-learning.md +0 -256
  50. package/skills/mom-test/references/question-patterns.md +0 -198
  51. package/skills/pandasai-analytics/SKILL.md +0 -251
  52. package/skills/release-it/SKILL.md +0 -235
  53. package/skills/release-it/references/anti-patterns.md +0 -279
  54. package/skills/release-it/references/capacity-planning.md +0 -285
  55. package/skills/release-it/references/chaos-engineering.md +0 -325
  56. package/skills/release-it/references/deployment-strategies.md +0 -331
  57. package/skills/release-it/references/observability.md +0 -301
  58. package/skills/release-it/references/stability-patterns.md +0 -355
  59. package/skills/skill-creator-ultra/.agents/workflows/skill-audit.md +0 -37
  60. package/skills/skill-creator-ultra/.agents/workflows/skill-compare.md +0 -34
  61. package/skills/skill-creator-ultra/.agents/workflows/skill-export.md +0 -51
  62. package/skills/skill-creator-ultra/.agents/workflows/skill-generate.md +0 -39
  63. package/skills/skill-creator-ultra/.agents/workflows/skill-scaffold.md +0 -52
  64. package/skills/skill-creator-ultra/.agents/workflows/skill-simulate.md +0 -25
  65. package/skills/skill-creator-ultra/.agents/workflows/skill-stats.md +0 -31
  66. package/skills/skill-creator-ultra/.agents/workflows/skill-validate.md +0 -25
  67. package/skills/skill-creator-ultra/README.md +0 -1242
  68. package/skills/skill-creator-ultra/SKILL.md +0 -388
  69. package/skills/skill-creator-ultra/agents/analyzer.md +0 -274
  70. package/skills/skill-creator-ultra/agents/comparator.md +0 -202
  71. package/skills/skill-creator-ultra/agents/grader.md +0 -223
  72. package/skills/skill-creator-ultra/assets/eval_review.html +0 -146
  73. package/skills/skill-creator-ultra/eval-viewer/generate_review.py +0 -471
  74. package/skills/skill-creator-ultra/eval-viewer/viewer.html +0 -1325
  75. package/skills/skill-creator-ultra/examples/example_anthropic_frontend.md +0 -109
  76. package/skills/skill-creator-ultra/examples/example_anthropic_pdf.md +0 -116
  77. package/skills/skill-creator-ultra/examples/example_api_docs.md +0 -189
  78. package/skills/skill-creator-ultra/examples/example_db_migration.md +0 -253
  79. package/skills/skill-creator-ultra/examples/example_git_commit.md +0 -111
  80. package/skills/skill-creator-ultra/install.ps1 +0 -289
  81. package/skills/skill-creator-ultra/install.sh +0 -313
  82. package/skills/skill-creator-ultra/phases/phase1_interview.md +0 -202
  83. package/skills/skill-creator-ultra/phases/phase2_extract.md +0 -55
  84. package/skills/skill-creator-ultra/phases/phase3_detect.md +0 -57
  85. package/skills/skill-creator-ultra/phases/phase4_generate.md +0 -543
  86. package/skills/skill-creator-ultra/phases/phase5_test.md +0 -319
  87. package/skills/skill-creator-ultra/phases/phase6_eval.md +0 -301
  88. package/skills/skill-creator-ultra/phases/phase7_iterate.md +0 -103
  89. package/skills/skill-creator-ultra/phases/phase8_optimize.md +0 -113
  90. package/skills/skill-creator-ultra/resources/advanced_patterns.md +0 -499
  91. package/skills/skill-creator-ultra/resources/anti_patterns.md +0 -376
  92. package/skills/skill-creator-ultra/resources/blueprints.md +0 -498
  93. package/skills/skill-creator-ultra/resources/checklist.md +0 -243
  94. package/skills/skill-creator-ultra/resources/composition_cookbook.md +0 -291
  95. package/skills/skill-creator-ultra/resources/description_optimization.md +0 -90
  96. package/skills/skill-creator-ultra/resources/eval_guide.md +0 -133
  97. package/skills/skill-creator-ultra/resources/industry_questions.md +0 -189
  98. package/skills/skill-creator-ultra/resources/interview_questions.md +0 -200
  99. package/skills/skill-creator-ultra/resources/pattern_detection.md +0 -200
  100. package/skills/skill-creator-ultra/resources/prompt_engineering.md +0 -531
  101. package/skills/skill-creator-ultra/resources/schemas.md +0 -430
  102. package/skills/skill-creator-ultra/resources/script_integration.md +0 -593
  103. package/skills/skill-creator-ultra/resources/scripts_guide.md +0 -339
  104. package/skills/skill-creator-ultra/resources/skill_template.md +0 -124
  105. package/skills/skill-creator-ultra/resources/skill_writing_guide.md +0 -634
  106. package/skills/skill-creator-ultra/resources/versioning_guide.md +0 -193
  107. package/skills/skill-creator-ultra/scripts/ci_eval.py +0 -200
  108. package/skills/skill-creator-ultra/scripts/package_skill.py +0 -165
  109. package/skills/skill-creator-ultra/scripts/simulate_skill.py +0 -398
  110. package/skills/skill-creator-ultra/scripts/skill_audit.py +0 -611
  111. package/skills/skill-creator-ultra/scripts/skill_compare.py +0 -265
  112. package/skills/skill-creator-ultra/scripts/skill_export.py +0 -334
  113. package/skills/skill-creator-ultra/scripts/skill_scaffold.py +0 -403
  114. package/skills/skill-creator-ultra/scripts/skill_stats.py +0 -339
  115. package/skills/skill-creator-ultra/scripts/validate_skill.py +0 -411
  116. package/skills/tailwind-mastery/SKILL.md +0 -229
  117. package/skills/vercel-react-best-practices/AGENTS.md +0 -3373
  118. package/skills/vercel-react-best-practices/README.md +0 -123
  119. package/skills/vercel-react-best-practices/SKILL.md +0 -143
  120. package/skills/vercel-react-best-practices/rules/_sections.md +0 -46
  121. package/skills/vercel-react-best-practices/rules/_template.md +0 -28
  122. package/skills/vercel-react-best-practices/rules/advanced-event-handler-refs.md +0 -55
  123. package/skills/vercel-react-best-practices/rules/advanced-init-once.md +0 -42
  124. package/skills/vercel-react-best-practices/rules/advanced-use-latest.md +0 -39
  125. package/skills/vercel-react-best-practices/rules/async-api-routes.md +0 -38
  126. package/skills/vercel-react-best-practices/rules/async-defer-await.md +0 -80
  127. package/skills/vercel-react-best-practices/rules/async-dependencies.md +0 -51
  128. package/skills/vercel-react-best-practices/rules/async-parallel.md +0 -28
  129. package/skills/vercel-react-best-practices/rules/async-suspense-boundaries.md +0 -99
  130. package/skills/vercel-react-best-practices/rules/bundle-barrel-imports.md +0 -59
  131. package/skills/vercel-react-best-practices/rules/bundle-conditional.md +0 -31
  132. package/skills/vercel-react-best-practices/rules/bundle-defer-third-party.md +0 -49
  133. package/skills/vercel-react-best-practices/rules/bundle-dynamic-imports.md +0 -35
  134. package/skills/vercel-react-best-practices/rules/bundle-preload.md +0 -50
  135. package/skills/vercel-react-best-practices/rules/client-event-listeners.md +0 -74
  136. package/skills/vercel-react-best-practices/rules/client-localstorage-schema.md +0 -71
  137. package/skills/vercel-react-best-practices/rules/client-passive-event-listeners.md +0 -48
  138. package/skills/vercel-react-best-practices/rules/client-swr-dedup.md +0 -56
  139. package/skills/vercel-react-best-practices/rules/js-batch-dom-css.md +0 -107
  140. package/skills/vercel-react-best-practices/rules/js-cache-function-results.md +0 -80
  141. package/skills/vercel-react-best-practices/rules/js-cache-property-access.md +0 -28
  142. package/skills/vercel-react-best-practices/rules/js-cache-storage.md +0 -70
  143. package/skills/vercel-react-best-practices/rules/js-combine-iterations.md +0 -32
  144. package/skills/vercel-react-best-practices/rules/js-early-exit.md +0 -50
  145. package/skills/vercel-react-best-practices/rules/js-flatmap-filter.md +0 -60
  146. package/skills/vercel-react-best-practices/rules/js-hoist-regexp.md +0 -45
  147. package/skills/vercel-react-best-practices/rules/js-index-maps.md +0 -37
  148. package/skills/vercel-react-best-practices/rules/js-length-check-first.md +0 -49
  149. package/skills/vercel-react-best-practices/rules/js-min-max-loop.md +0 -82
  150. package/skills/vercel-react-best-practices/rules/js-set-map-lookups.md +0 -24
  151. package/skills/vercel-react-best-practices/rules/js-tosorted-immutable.md +0 -57
  152. package/skills/vercel-react-best-practices/rules/rendering-activity.md +0 -26
  153. package/skills/vercel-react-best-practices/rules/rendering-animate-svg-wrapper.md +0 -47
  154. package/skills/vercel-react-best-practices/rules/rendering-conditional-render.md +0 -40
  155. package/skills/vercel-react-best-practices/rules/rendering-content-visibility.md +0 -38
  156. package/skills/vercel-react-best-practices/rules/rendering-hoist-jsx.md +0 -46
  157. package/skills/vercel-react-best-practices/rules/rendering-hydration-no-flicker.md +0 -82
  158. package/skills/vercel-react-best-practices/rules/rendering-hydration-suppress-warning.md +0 -30
  159. package/skills/vercel-react-best-practices/rules/rendering-resource-hints.md +0 -85
  160. package/skills/vercel-react-best-practices/rules/rendering-script-defer-async.md +0 -68
  161. package/skills/vercel-react-best-practices/rules/rendering-svg-precision.md +0 -28
  162. package/skills/vercel-react-best-practices/rules/rendering-usetransition-loading.md +0 -75
  163. package/skills/vercel-react-best-practices/rules/rerender-defer-reads.md +0 -39
  164. package/skills/vercel-react-best-practices/rules/rerender-dependencies.md +0 -45
  165. package/skills/vercel-react-best-practices/rules/rerender-derived-state-no-effect.md +0 -40
  166. package/skills/vercel-react-best-practices/rules/rerender-derived-state.md +0 -29
  167. package/skills/vercel-react-best-practices/rules/rerender-functional-setstate.md +0 -74
  168. package/skills/vercel-react-best-practices/rules/rerender-lazy-state-init.md +0 -58
  169. package/skills/vercel-react-best-practices/rules/rerender-memo-with-default-value.md +0 -38
  170. package/skills/vercel-react-best-practices/rules/rerender-memo.md +0 -44
  171. package/skills/vercel-react-best-practices/rules/rerender-move-effect-to-event.md +0 -45
  172. package/skills/vercel-react-best-practices/rules/rerender-no-inline-components.md +0 -82
  173. package/skills/vercel-react-best-practices/rules/rerender-simple-expression-in-memo.md +0 -35
  174. package/skills/vercel-react-best-practices/rules/rerender-split-combined-hooks.md +0 -64
  175. package/skills/vercel-react-best-practices/rules/rerender-transitions.md +0 -40
  176. package/skills/vercel-react-best-practices/rules/rerender-use-deferred-value.md +0 -59
  177. package/skills/vercel-react-best-practices/rules/rerender-use-ref-transient-values.md +0 -73
  178. package/skills/vercel-react-best-practices/rules/server-after-nonblocking.md +0 -73
  179. package/skills/vercel-react-best-practices/rules/server-auth-actions.md +0 -96
  180. package/skills/vercel-react-best-practices/rules/server-cache-lru.md +0 -41
  181. package/skills/vercel-react-best-practices/rules/server-cache-react.md +0 -76
  182. package/skills/vercel-react-best-practices/rules/server-dedup-props.md +0 -65
  183. package/skills/vercel-react-best-practices/rules/server-hoist-static-io.md +0 -142
  184. package/skills/vercel-react-best-practices/rules/server-parallel-fetching.md +0 -83
  185. package/skills/vercel-react-best-practices/rules/server-serialization.md +0 -38
  186. package/skills/web-design-guidelines/SKILL.md +0 -39
@@ -0,0 +1,400 @@
1
+ #!/usr/bin/env node
2
+ "use strict";
3
+ /**
4
+ * CodyMaster MCP Context Server
5
+ *
6
+ * Exposes 7 tools over JSON-RPC 2.0 / stdio (Content-Length framing):
7
+ * cm_query — FTS5 search across learnings + decisions
8
+ * cm_resolve — resolve a cm:// URI at L0/L1/L2
9
+ * cm_bus_read — read context bus state
10
+ * cm_bus_write — publish skill output to context bus
11
+ * cm_budget_check — check token budget for a category
12
+ * cm_memory_decay — TTL cleanup for learnings
13
+ * cm_index_refresh — regenerate L0 indexes
14
+ *
15
+ * Usage (stdio MCP):
16
+ * node dist/mcp-context-server.js --project /path/to/project
17
+ *
18
+ * Claude Desktop config:
19
+ * {
20
+ * "mcpServers": {
21
+ * "cm-context": {
22
+ * "command": "node",
23
+ * "args": ["/path/to/dist/mcp-context-server.js", "--project", "/path/to/project"]
24
+ * }
25
+ * }
26
+ * }
27
+ */
28
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
29
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
30
+ return new (P || (P = Promise))(function (resolve, reject) {
31
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
32
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
33
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
34
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
35
+ });
36
+ };
37
+ var __importDefault = (this && this.__importDefault) || function (mod) {
38
+ return (mod && mod.__esModule) ? mod : { "default": mod };
39
+ };
40
+ Object.defineProperty(exports, "__esModule", { value: true });
41
+ const path_1 = __importDefault(require("path"));
42
+ const context_db_1 = require("./context-db");
43
+ const uri_resolver_1 = require("./uri-resolver");
44
+ const context_bus_1 = require("./context-bus");
45
+ const token_budget_1 = require("./token-budget");
46
+ const l0_indexer_1 = require("./l0-indexer");
47
+ // ─── Config ──────────────────────────────────────────────────────────────────
48
+ const SERVER_NAME = 'cm-context';
49
+ const SERVER_VERSION = '1.0.0';
50
+ function getProjectPath() {
51
+ const args = process.argv.slice(2);
52
+ const idx = args.indexOf('--project');
53
+ if (idx !== -1 && args[idx + 1])
54
+ return path_1.default.resolve(args[idx + 1]);
55
+ return process.env.CM_PROJECT_PATH ? path_1.default.resolve(process.env.CM_PROJECT_PATH) : process.cwd();
56
+ }
57
+ const PROJECT_PATH = getProjectPath();
58
+ function cmQuery(args) {
59
+ const { query = '', scope = 'all', filter_scope, limit = 10 } = args;
60
+ const dbPath = (0, context_db_1.getDbPath)(PROJECT_PATH);
61
+ (0, context_db_1.openDb)(dbPath);
62
+ const results = [];
63
+ if (scope === 'all' || scope === 'learnings') {
64
+ const learnings = (0, context_db_1.queryLearnings)(dbPath, query, filter_scope, limit);
65
+ for (const l of learnings) {
66
+ results.push(Object.assign({ type: 'learning' }, l));
67
+ }
68
+ }
69
+ if (scope === 'all' || scope === 'decisions') {
70
+ const decisions = (0, context_db_1.queryDecisions)(dbPath, query, limit);
71
+ for (const d of decisions) {
72
+ results.push(Object.assign({ type: 'decision' }, d));
73
+ }
74
+ }
75
+ return {
76
+ query,
77
+ scope,
78
+ count: results.length,
79
+ results,
80
+ };
81
+ }
82
+ function cmResolve(args) {
83
+ const { uri, depth = 'L1' } = args;
84
+ const resolved = (0, uri_resolver_1.resolve)(uri, PROJECT_PATH, depth);
85
+ return {
86
+ uri: resolved.uri,
87
+ depth: resolved.depth,
88
+ found: resolved.found,
89
+ tokenEstimate: resolved.tokenEstimate,
90
+ content: resolved.content,
91
+ };
92
+ }
93
+ function cmBusRead() {
94
+ const bus = (0, context_bus_1.readBus)(PROJECT_PATH);
95
+ if (!bus) {
96
+ return { active: false, message: 'No active context bus. Start a skill chain first.' };
97
+ }
98
+ return { active: true, bus };
99
+ }
100
+ function cmBusWrite(args) {
101
+ const { skill, summary, affected_files, output_path, metadata } = args;
102
+ if (!skill)
103
+ throw new Error('skill is required');
104
+ (0, context_bus_1.updateBusStep)(PROJECT_PATH, skill, {
105
+ summary: summary !== null && summary !== void 0 ? summary : '',
106
+ output_path: output_path !== null && output_path !== void 0 ? output_path : '',
107
+ affected_files: affected_files !== null && affected_files !== void 0 ? affected_files : [],
108
+ metadata: metadata !== null && metadata !== void 0 ? metadata : {},
109
+ });
110
+ const bus = (0, context_bus_1.readBus)(PROJECT_PATH);
111
+ return {
112
+ ok: true,
113
+ skill,
114
+ current_step: bus === null || bus === void 0 ? void 0 : bus.current_step,
115
+ pipeline: bus === null || bus === void 0 ? void 0 : bus.pipeline,
116
+ };
117
+ }
118
+ function cmBudgetCheck(args) {
119
+ const { category, text, token_count } = args;
120
+ if (!category)
121
+ throw new Error('category is required');
122
+ const budget = (0, token_budget_1.loadBudget)(PROJECT_PATH);
123
+ const tokens = token_count !== null && token_count !== void 0 ? token_count : (text ? (0, token_budget_1.estimateTokens)(text) : 0);
124
+ const check = (0, token_budget_1.checkBudget)(budget, category, tokens);
125
+ return {
126
+ category,
127
+ tokens_requested: tokens,
128
+ allowed: check.allowed,
129
+ remaining: check.remaining,
130
+ suggestion: check.suggestion,
131
+ };
132
+ }
133
+ function cmMemoryDecay(args) {
134
+ const { dry_run = false } = args;
135
+ const dbPath = (0, context_db_1.getDbPath)(PROJECT_PATH);
136
+ const db = (0, context_db_1.openDb)(dbPath);
137
+ const now = new Date();
138
+ // Find learnings past TTL
139
+ const candidates = db.prepare(`
140
+ SELECT id, what_failed, created_at, ttl
141
+ FROM learnings
142
+ WHERE status = 'active'
143
+ AND ttl IS NOT NULL
144
+ AND ttl > 0
145
+ `).all();
146
+ const expired = [];
147
+ for (const row of candidates) {
148
+ const created = new Date(row.created_at);
149
+ const daysSince = (now.getTime() - created.getTime()) / (1000 * 60 * 60 * 24);
150
+ if (daysSince >= row.ttl) {
151
+ expired.push(row.id);
152
+ }
153
+ }
154
+ if (!dry_run && expired.length > 0) {
155
+ const placeholders = expired.map(() => '?').join(',');
156
+ db.prepare(`UPDATE learnings SET status = 'archived' WHERE id IN (${placeholders})`).run(...expired);
157
+ }
158
+ return {
159
+ dry_run,
160
+ expired_count: expired.length,
161
+ expired_ids: expired,
162
+ message: dry_run
163
+ ? `${expired.length} learnings would be archived (dry run)`
164
+ : `${expired.length} learnings archived`,
165
+ };
166
+ }
167
+ function cmIndexRefresh(args) {
168
+ const { target = 'all' } = args;
169
+ if (target === 'all') {
170
+ const result = (0, l0_indexer_1.refreshAllIndexes)(PROJECT_PATH);
171
+ return {
172
+ target,
173
+ learnings: { generated: true, tokens: (0, token_budget_1.estimateTokens)(result.learnings) },
174
+ skeleton: { generated: true, tokens: (0, token_budget_1.estimateTokens)(result.skeleton) },
175
+ };
176
+ }
177
+ if (target === 'learnings') {
178
+ const { generateLearningsIndex } = require('./l0-indexer');
179
+ const content = generateLearningsIndex(PROJECT_PATH);
180
+ return { target, learnings: { generated: true, tokens: (0, token_budget_1.estimateTokens)(content) } };
181
+ }
182
+ if (target === 'skeleton') {
183
+ const { generateSkeletonIndex } = require('./l0-indexer');
184
+ const content = generateSkeletonIndex(PROJECT_PATH);
185
+ return { target, skeleton: { generated: true, tokens: (0, token_budget_1.estimateTokens)(content) } };
186
+ }
187
+ throw new Error(`Unknown target: ${target}. Valid: learnings, skeleton, all`);
188
+ }
189
+ // ─── Tool Registry ─────────────────────────────────────────────────────────────
190
+ const TOOLS = [
191
+ {
192
+ name: 'cm_query',
193
+ description: 'FTS5 semantic search across CodyMaster learnings and decisions stored in SQLite.',
194
+ inputSchema: {
195
+ type: 'object',
196
+ properties: {
197
+ query: { type: 'string', description: 'Search query (FTS5 syntax supported)' },
198
+ scope: {
199
+ type: 'string',
200
+ enum: ['learnings', 'decisions', 'all'],
201
+ description: 'Which collection to search (default: all)',
202
+ },
203
+ filter_scope: {
204
+ type: 'string',
205
+ description: 'Optional scope filter for learnings (e.g. "module", "global")',
206
+ },
207
+ limit: { type: 'number', description: 'Max results per collection (default: 10)' },
208
+ },
209
+ required: ['query'],
210
+ },
211
+ },
212
+ {
213
+ name: 'cm_resolve',
214
+ description: 'Resolve a cm:// URI to content at the specified depth (L0=compact, L1=overview, L2=full).',
215
+ inputSchema: {
216
+ type: 'object',
217
+ properties: {
218
+ uri: {
219
+ type: 'string',
220
+ description: 'cm:// URI (e.g. cm://memory/learnings, cm://skills/cm-tdd, cm://pipeline/current)',
221
+ },
222
+ depth: {
223
+ type: 'string',
224
+ enum: ['L0', 'L1', 'L2'],
225
+ description: 'Loading depth (default: L1)',
226
+ },
227
+ },
228
+ required: ['uri'],
229
+ },
230
+ },
231
+ {
232
+ name: 'cm_bus_read',
233
+ description: 'Read the current context bus state — pipeline name, current step, and shared skill outputs.',
234
+ inputSchema: { type: 'object', properties: {} },
235
+ },
236
+ {
237
+ name: 'cm_bus_write',
238
+ description: 'Publish a skill completion event to the context bus so subsequent skills can read it.',
239
+ inputSchema: {
240
+ type: 'object',
241
+ properties: {
242
+ skill: { type: 'string', description: 'Skill name (e.g. cm-brainstorm-idea)' },
243
+ summary: { type: 'string', description: 'Human-readable outcome summary' },
244
+ affected_files: {
245
+ type: 'array',
246
+ items: { type: 'string' },
247
+ description: 'Files created/modified by this skill',
248
+ },
249
+ output_path: { type: 'string', description: 'Primary output file path' },
250
+ metadata: { type: 'object', description: 'Arbitrary key-value metadata' },
251
+ },
252
+ required: ['skill'],
253
+ },
254
+ },
255
+ {
256
+ name: 'cm_budget_check',
257
+ description: 'Check whether loading content for a given category is within token budget.',
258
+ inputSchema: {
259
+ type: 'object',
260
+ properties: {
261
+ category: {
262
+ type: 'string',
263
+ description: 'Budget category (e.g. skill_index_L0, memory_learnings, context_retrieval)',
264
+ },
265
+ text: { type: 'string', description: 'Text to estimate tokens for (optional)' },
266
+ token_count: { type: 'number', description: 'Pre-computed token count (overrides text)' },
267
+ },
268
+ required: ['category'],
269
+ },
270
+ },
271
+ {
272
+ name: 'cm_memory_decay',
273
+ description: 'Archive learnings whose TTL has expired. Run periodically to keep the memory lean.',
274
+ inputSchema: {
275
+ type: 'object',
276
+ properties: {
277
+ dry_run: {
278
+ type: 'boolean',
279
+ description: 'If true, reports what would be archived without changing data (default: false)',
280
+ },
281
+ },
282
+ },
283
+ },
284
+ {
285
+ name: 'cm_index_refresh',
286
+ description: 'Regenerate L0 compact indexes for learnings and/or skeleton to keep context fresh.',
287
+ inputSchema: {
288
+ type: 'object',
289
+ properties: {
290
+ target: {
291
+ type: 'string',
292
+ enum: ['learnings', 'skeleton', 'all'],
293
+ description: 'Which index to refresh (default: all)',
294
+ },
295
+ },
296
+ },
297
+ },
298
+ ];
299
+ // ─── MCP stdio protocol (JSON-RPC 2.0, Content-Length framing) ───────────────
300
+ function sendMessage(msg) {
301
+ const json = JSON.stringify(msg);
302
+ const header = `Content-Length: ${Buffer.byteLength(json)}\r\n\r\n`;
303
+ process.stdout.write(header + json);
304
+ }
305
+ function respond(id, result) {
306
+ sendMessage({ jsonrpc: '2.0', id, result });
307
+ }
308
+ function respondError(id, code, message) {
309
+ sendMessage({ jsonrpc: '2.0', id, error: { code, message } });
310
+ }
311
+ function handleRequest(msg) {
312
+ return __awaiter(this, void 0, void 0, function* () {
313
+ const { id, method, params } = msg;
314
+ if (method === 'initialize') {
315
+ respond(id, {
316
+ protocolVersion: '2024-11-05',
317
+ capabilities: { tools: {} },
318
+ serverInfo: { name: SERVER_NAME, version: SERVER_VERSION },
319
+ });
320
+ return;
321
+ }
322
+ if (method === 'notifications/initialized')
323
+ return;
324
+ if (method === 'tools/list') {
325
+ respond(id, { tools: TOOLS });
326
+ return;
327
+ }
328
+ if (method === 'tools/call') {
329
+ const { name, arguments: args } = (params || {});
330
+ try {
331
+ let result;
332
+ const a = args || {};
333
+ if (name === 'cm_query')
334
+ result = cmQuery(a);
335
+ else if (name === 'cm_resolve')
336
+ result = cmResolve(a);
337
+ else if (name === 'cm_bus_read')
338
+ result = cmBusRead();
339
+ else if (name === 'cm_bus_write')
340
+ result = cmBusWrite(a);
341
+ else if (name === 'cm_budget_check')
342
+ result = cmBudgetCheck(a);
343
+ else if (name === 'cm_memory_decay')
344
+ result = cmMemoryDecay(a);
345
+ else if (name === 'cm_index_refresh')
346
+ result = cmIndexRefresh(a);
347
+ else
348
+ throw new Error(`Unknown tool: ${name}`);
349
+ respond(id, {
350
+ content: [{ type: 'text', text: JSON.stringify(result, null, 2) }],
351
+ });
352
+ }
353
+ catch (err) {
354
+ respond(id, {
355
+ content: [{ type: 'text', text: `Error: ${err.message}` }],
356
+ isError: true,
357
+ });
358
+ }
359
+ return;
360
+ }
361
+ if (id !== undefined) {
362
+ respondError(id, -32601, `Method not found: ${method}`);
363
+ }
364
+ });
365
+ }
366
+ // ─── Stdin reader (Content-Length framed) ────────────────────────────────────
367
+ let buffer = Buffer.alloc(0);
368
+ process.stdin.on('data', (chunk) => __awaiter(void 0, void 0, void 0, function* () {
369
+ buffer = Buffer.concat([buffer, chunk]);
370
+ while (true) {
371
+ const sep = buffer.indexOf('\r\n\r\n');
372
+ if (sep === -1)
373
+ break;
374
+ const header = buffer.slice(0, sep).toString();
375
+ const match = header.match(/Content-Length:\s*(\d+)/i);
376
+ if (!match) {
377
+ buffer = buffer.slice(sep + 4);
378
+ break;
379
+ }
380
+ const contentLength = parseInt(match[1], 10);
381
+ const bodyStart = sep + 4;
382
+ if (buffer.length < bodyStart + contentLength)
383
+ break;
384
+ const body = buffer.slice(bodyStart, bodyStart + contentLength).toString('utf8');
385
+ buffer = buffer.slice(bodyStart + contentLength);
386
+ try {
387
+ const msg = JSON.parse(body);
388
+ yield handleRequest(msg);
389
+ }
390
+ catch (_a) {
391
+ // ignore malformed messages
392
+ }
393
+ }
394
+ }));
395
+ process.stdin.on('end', () => {
396
+ (0, context_db_1.closeDb)((0, context_db_1.getDbPath)(PROJECT_PATH));
397
+ process.exit(0);
398
+ });
399
+ process.on('SIGTERM', () => { (0, context_db_1.closeDb)((0, context_db_1.getDbPath)(PROJECT_PATH)); process.exit(0); });
400
+ process.on('SIGINT', () => { (0, context_db_1.closeDb)((0, context_db_1.getDbPath)(PROJECT_PATH)); process.exit(0); });
@@ -0,0 +1,126 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.migrateJsonToSqlite = migrateJsonToSqlite;
7
+ exports.exportSqliteToJson = exportSqliteToJson;
8
+ const fs_1 = __importDefault(require("fs"));
9
+ const path_1 = __importDefault(require("path"));
10
+ const context_db_1 = require("./context-db");
11
+ function migrateJsonToSqlite(projectPath) {
12
+ var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q, _r, _s, _t, _u, _v, _w, _x, _y, _z, _0, _1, _2, _3;
13
+ const cmDir = path_1.default.join(projectPath, '.cm');
14
+ const dbPath = (0, context_db_1.getDbPath)(projectPath);
15
+ (0, context_db_1.openDb)(dbPath);
16
+ const result = {
17
+ learnings: { migrated: 0, skipped: 0 },
18
+ decisions: { migrated: 0, skipped: 0 },
19
+ dbPath,
20
+ backupCreated: false,
21
+ };
22
+ // ── Migrate learnings ─────────────────────────────────────────────────────
23
+ const learningsPath = path_1.default.join(cmDir, 'memory', 'learnings.json');
24
+ if (fs_1.default.existsSync(learningsPath)) {
25
+ // Backup
26
+ const backupPath = learningsPath + '.backup';
27
+ fs_1.default.copyFileSync(learningsPath, backupPath);
28
+ result.backupCreated = true;
29
+ let raw = [];
30
+ try {
31
+ raw = JSON.parse(fs_1.default.readFileSync(learningsPath, 'utf-8'));
32
+ }
33
+ catch ( /* invalid JSON — skip */_4) { /* invalid JSON — skip */ }
34
+ for (const l of raw) {
35
+ try {
36
+ const now = new Date().toISOString();
37
+ const learning = {
38
+ id: (_a = l.id) !== null && _a !== void 0 ? _a : `L-${Date.now()}-${Math.random().toString(36).slice(2, 7)}`,
39
+ what_failed: (_d = (_c = (_b = l.whatFailed) !== null && _b !== void 0 ? _b : l.what_failed) !== null && _c !== void 0 ? _c : l.error) !== null && _d !== void 0 ? _d : '(unknown)',
40
+ why_failed: (_g = (_f = (_e = l.whyFailed) !== null && _e !== void 0 ? _e : l.why_failed) !== null && _f !== void 0 ? _f : l.cause) !== null && _g !== void 0 ? _g : '',
41
+ how_to_prevent: (_k = (_j = (_h = l.howToPrevent) !== null && _h !== void 0 ? _h : l.how_to_prevent) !== null && _j !== void 0 ? _j : l.prevention) !== null && _k !== void 0 ? _k : '',
42
+ scope: (_l = l.scope) !== null && _l !== void 0 ? _l : 'global',
43
+ ttl: (_m = l.ttl) !== null && _m !== void 0 ? _m : 60,
44
+ reinforce_count: (_p = (_o = l.reinforceCount) !== null && _o !== void 0 ? _o : l.reinforce_count) !== null && _p !== void 0 ? _p : 0,
45
+ status: (_q = l.status) !== null && _q !== void 0 ? _q : 'active',
46
+ created_at: (_s = (_r = l.date) !== null && _r !== void 0 ? _r : l.timestamp) !== null && _s !== void 0 ? _s : now,
47
+ updated_at: (_u = (_t = l.date) !== null && _t !== void 0 ? _t : l.timestamp) !== null && _u !== void 0 ? _u : now,
48
+ agent: l.agent,
49
+ task_id: (_v = l.taskId) !== null && _v !== void 0 ? _v : l.task_id,
50
+ module: l.module,
51
+ };
52
+ (0, context_db_1.insertLearning)(dbPath, learning);
53
+ result.learnings.migrated++;
54
+ }
55
+ catch (_5) {
56
+ result.learnings.skipped++;
57
+ }
58
+ }
59
+ }
60
+ // ── Migrate decisions ─────────────────────────────────────────────────────
61
+ const decisionsPath = path_1.default.join(cmDir, 'memory', 'decisions.json');
62
+ if (fs_1.default.existsSync(decisionsPath)) {
63
+ const backupPath = decisionsPath + '.backup';
64
+ fs_1.default.copyFileSync(decisionsPath, backupPath);
65
+ let raw = [];
66
+ try {
67
+ raw = JSON.parse(fs_1.default.readFileSync(decisionsPath, 'utf-8'));
68
+ }
69
+ catch ( /* invalid JSON — skip */_6) { /* invalid JSON — skip */ }
70
+ for (const d of raw) {
71
+ try {
72
+ const now = new Date().toISOString();
73
+ const decision = {
74
+ id: (_w = d.id) !== null && _w !== void 0 ? _w : `D-${Date.now()}-${Math.random().toString(36).slice(2, 7)}`,
75
+ decision: (_x = d.decision) !== null && _x !== void 0 ? _x : '(unknown)',
76
+ rationale: (_y = d.rationale) !== null && _y !== void 0 ? _y : '',
77
+ scope: (_z = d.scope) !== null && _z !== void 0 ? _z : 'global',
78
+ status: (_0 = d.status) !== null && _0 !== void 0 ? _0 : 'active',
79
+ superseded_by: (_1 = d.supersededBy) !== null && _1 !== void 0 ? _1 : d.superseded_by,
80
+ created_at: (_3 = (_2 = d.date) !== null && _2 !== void 0 ? _2 : d.timestamp) !== null && _3 !== void 0 ? _3 : now,
81
+ agent: d.agent,
82
+ };
83
+ (0, context_db_1.insertDecision)(dbPath, decision);
84
+ result.decisions.migrated++;
85
+ }
86
+ catch (_7) {
87
+ result.decisions.skipped++;
88
+ }
89
+ }
90
+ }
91
+ return result;
92
+ }
93
+ function exportSqliteToJson(projectPath) {
94
+ const cmDir = path_1.default.join(projectPath, '.cm');
95
+ const memDir = path_1.default.join(cmDir, 'memory');
96
+ const dbPath = (0, context_db_1.getDbPath)(projectPath);
97
+ const db = (0, context_db_1.openDb)(dbPath);
98
+ fs_1.default.mkdirSync(memDir, { recursive: true });
99
+ // Export learnings
100
+ const learnings = db.prepare(`
101
+ SELECT id, what_failed, why_failed, how_to_prevent, scope, ttl,
102
+ reinforce_count as reinforceCount, status, created_at as date,
103
+ agent, task_id as taskId, module
104
+ FROM learnings
105
+ WHERE status != 'archived'
106
+ ORDER BY created_at DESC
107
+ `).all();
108
+ const learningsPath = path_1.default.join(memDir, 'learnings.json');
109
+ fs_1.default.writeFileSync(learningsPath, JSON.stringify(learnings, null, 2), 'utf-8');
110
+ // Export decisions
111
+ const decisions = db.prepare(`
112
+ SELECT id, decision, rationale, scope, status,
113
+ superseded_by as supersededBy, created_at as date, agent
114
+ FROM decisions
115
+ WHERE status != 'archived'
116
+ ORDER BY created_at DESC
117
+ `).all();
118
+ const decisionsPath = path_1.default.join(memDir, 'decisions.json');
119
+ fs_1.default.writeFileSync(decisionsPath, JSON.stringify(decisions, null, 2), 'utf-8');
120
+ return {
121
+ learnings: learnings.length,
122
+ decisions: decisions.length,
123
+ learningsPath,
124
+ decisionsPath,
125
+ };
126
+ }
@@ -16,6 +16,7 @@ exports.formatChainProgressBar = formatChainProgressBar;
16
16
  exports.getCurrentSkill = getCurrentSkill;
17
17
  const crypto_1 = __importDefault(require("crypto"));
18
18
  const builtin_1 = require("./chains/builtin");
19
+ const context_bus_1 = require("./context-bus");
19
20
  // ─── Chain Matching ─────────────────────────────────────────────────────────
20
21
  // TRIZ #10: Preliminary Action — analyze task BEFORE dispatching
21
22
  /**
@@ -59,7 +60,7 @@ function findChain(chainId) {
59
60
  /**
60
61
  * Create a new chain execution from a chain definition.
61
62
  */
62
- function createChainExecution(chain, projectId, taskTitle, agent) {
63
+ function createChainExecution(chain, projectId, taskTitle, agent, projectPath) {
63
64
  const now = new Date().toISOString();
64
65
  const steps = chain.steps.map((step, index) => ({
65
66
  index,
@@ -74,7 +75,7 @@ function createChainExecution(chain, projectId, taskTitle, agent) {
74
75
  steps[0].status = 'running';
75
76
  steps[0].startedAt = now;
76
77
  }
77
- return {
78
+ const execution = {
78
79
  id: crypto_1.default.randomUUID(),
79
80
  chainId: chain.id,
80
81
  chainName: chain.name,
@@ -87,12 +88,20 @@ function createChainExecution(chain, projectId, taskTitle, agent) {
87
88
  startedAt: now,
88
89
  updatedAt: now,
89
90
  };
91
+ // Init context bus for this chain execution
92
+ if (projectPath) {
93
+ try {
94
+ (0, context_bus_1.initBus)(projectPath, chain.id, execution.id);
95
+ }
96
+ catch ( /* non-fatal: context bus is optional enhancement */_a) { /* non-fatal: context bus is optional enhancement */ }
97
+ }
98
+ return execution;
90
99
  }
91
100
  /**
92
101
  * Advance the chain to the next step. Marks current step as completed.
93
102
  * Returns the next step's skill name, or null if chain is complete.
94
103
  */
95
- function advanceChain(execution, output) {
104
+ function advanceChain(execution, output, projectPath) {
96
105
  const now = new Date().toISOString();
97
106
  const currentStep = execution.steps[execution.currentStepIndex];
98
107
  if (!currentStep) {
@@ -104,6 +113,13 @@ function advanceChain(execution, output) {
104
113
  if (output)
105
114
  currentStep.output = output;
106
115
  execution.updatedAt = now;
116
+ // Update context bus with completed step's output
117
+ if (projectPath) {
118
+ try {
119
+ (0, context_bus_1.updateBusStep)(projectPath, currentStep.skill, { summary: output });
120
+ }
121
+ catch ( /* non-fatal */_a) { /* non-fatal */ }
122
+ }
107
123
  // Find next non-skipped step
108
124
  let nextIndex = execution.currentStepIndex + 1;
109
125
  while (nextIndex < execution.steps.length) {