genesis-ai-cli 7.4.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (227) hide show
  1. package/.env.example +78 -0
  2. package/README.md +282 -0
  3. package/dist/src/active-inference/actions.d.ts +75 -0
  4. package/dist/src/active-inference/actions.js +250 -0
  5. package/dist/src/active-inference/autonomous-loop.d.ts +103 -0
  6. package/dist/src/active-inference/autonomous-loop.js +289 -0
  7. package/dist/src/active-inference/core.d.ts +85 -0
  8. package/dist/src/active-inference/core.js +555 -0
  9. package/dist/src/active-inference/demo-autonomous-loop.d.ts +8 -0
  10. package/dist/src/active-inference/demo-autonomous-loop.js +338 -0
  11. package/dist/src/active-inference/demo-value-integration.d.ts +8 -0
  12. package/dist/src/active-inference/demo-value-integration.js +174 -0
  13. package/dist/src/active-inference/index.d.ts +32 -0
  14. package/dist/src/active-inference/index.js +88 -0
  15. package/dist/src/active-inference/integration.d.ts +114 -0
  16. package/dist/src/active-inference/integration.js +698 -0
  17. package/dist/src/active-inference/memory-integration.d.ts +51 -0
  18. package/dist/src/active-inference/memory-integration.js +232 -0
  19. package/dist/src/active-inference/observations.d.ts +67 -0
  20. package/dist/src/active-inference/observations.js +147 -0
  21. package/dist/src/active-inference/test-active-inference.d.ts +8 -0
  22. package/dist/src/active-inference/test-active-inference.js +320 -0
  23. package/dist/src/active-inference/test-value-integration.d.ts +6 -0
  24. package/dist/src/active-inference/test-value-integration.js +168 -0
  25. package/dist/src/active-inference/types.d.ts +150 -0
  26. package/dist/src/active-inference/types.js +59 -0
  27. package/dist/src/active-inference/value-integration.d.ts +164 -0
  28. package/dist/src/active-inference/value-integration.js +459 -0
  29. package/dist/src/agents/base-agent.d.ts +53 -0
  30. package/dist/src/agents/base-agent.js +178 -0
  31. package/dist/src/agents/builder.d.ts +67 -0
  32. package/dist/src/agents/builder.js +537 -0
  33. package/dist/src/agents/critic.d.ts +35 -0
  34. package/dist/src/agents/critic.js +322 -0
  35. package/dist/src/agents/ethicist.d.ts +54 -0
  36. package/dist/src/agents/ethicist.js +393 -0
  37. package/dist/src/agents/explorer.d.ts +26 -0
  38. package/dist/src/agents/explorer.js +216 -0
  39. package/dist/src/agents/feeling.d.ts +41 -0
  40. package/dist/src/agents/feeling.js +320 -0
  41. package/dist/src/agents/index.d.ts +111 -0
  42. package/dist/src/agents/index.js +222 -0
  43. package/dist/src/agents/memory.d.ts +69 -0
  44. package/dist/src/agents/memory.js +404 -0
  45. package/dist/src/agents/message-bus.d.ts +88 -0
  46. package/dist/src/agents/message-bus.js +267 -0
  47. package/dist/src/agents/narrator.d.ts +90 -0
  48. package/dist/src/agents/narrator.js +473 -0
  49. package/dist/src/agents/planner.d.ts +38 -0
  50. package/dist/src/agents/planner.js +341 -0
  51. package/dist/src/agents/predictor.d.ts +73 -0
  52. package/dist/src/agents/predictor.js +506 -0
  53. package/dist/src/agents/sensor.d.ts +88 -0
  54. package/dist/src/agents/sensor.js +377 -0
  55. package/dist/src/agents/test-agents.d.ts +6 -0
  56. package/dist/src/agents/test-agents.js +73 -0
  57. package/dist/src/agents/types.d.ts +194 -0
  58. package/dist/src/agents/types.js +7 -0
  59. package/dist/src/brain/index.d.ts +185 -0
  60. package/dist/src/brain/index.js +843 -0
  61. package/dist/src/brain/trace.d.ts +91 -0
  62. package/dist/src/brain/trace.js +327 -0
  63. package/dist/src/brain/types.d.ts +165 -0
  64. package/dist/src/brain/types.js +51 -0
  65. package/dist/src/cli/chat.d.ts +237 -0
  66. package/dist/src/cli/chat.js +1959 -0
  67. package/dist/src/cli/dispatcher.d.ts +182 -0
  68. package/dist/src/cli/dispatcher.js +718 -0
  69. package/dist/src/cli/human-loop.d.ts +170 -0
  70. package/dist/src/cli/human-loop.js +543 -0
  71. package/dist/src/cli/index.d.ts +12 -0
  72. package/dist/src/cli/index.js +28 -0
  73. package/dist/src/cli/interactive.d.ts +141 -0
  74. package/dist/src/cli/interactive.js +757 -0
  75. package/dist/src/cli/ui.d.ts +205 -0
  76. package/dist/src/cli/ui.js +632 -0
  77. package/dist/src/consciousness/attention-schema.d.ts +154 -0
  78. package/dist/src/consciousness/attention-schema.js +432 -0
  79. package/dist/src/consciousness/global-workspace.d.ts +149 -0
  80. package/dist/src/consciousness/global-workspace.js +422 -0
  81. package/dist/src/consciousness/index.d.ts +186 -0
  82. package/dist/src/consciousness/index.js +476 -0
  83. package/dist/src/consciousness/phi-calculator.d.ts +119 -0
  84. package/dist/src/consciousness/phi-calculator.js +445 -0
  85. package/dist/src/consciousness/phi-decisions.d.ts +169 -0
  86. package/dist/src/consciousness/phi-decisions.js +383 -0
  87. package/dist/src/consciousness/phi-monitor.d.ts +153 -0
  88. package/dist/src/consciousness/phi-monitor.js +465 -0
  89. package/dist/src/consciousness/types.d.ts +260 -0
  90. package/dist/src/consciousness/types.js +44 -0
  91. package/dist/src/daemon/dream-mode.d.ts +115 -0
  92. package/dist/src/daemon/dream-mode.js +470 -0
  93. package/dist/src/daemon/index.d.ts +162 -0
  94. package/dist/src/daemon/index.js +542 -0
  95. package/dist/src/daemon/maintenance.d.ts +139 -0
  96. package/dist/src/daemon/maintenance.js +549 -0
  97. package/dist/src/daemon/process.d.ts +82 -0
  98. package/dist/src/daemon/process.js +442 -0
  99. package/dist/src/daemon/scheduler.d.ts +90 -0
  100. package/dist/src/daemon/scheduler.js +494 -0
  101. package/dist/src/daemon/types.d.ts +213 -0
  102. package/dist/src/daemon/types.js +50 -0
  103. package/dist/src/epistemic/index.d.ts +74 -0
  104. package/dist/src/epistemic/index.js +225 -0
  105. package/dist/src/grounding/epistemic-stack.d.ts +100 -0
  106. package/dist/src/grounding/epistemic-stack.js +408 -0
  107. package/dist/src/grounding/feedback.d.ts +98 -0
  108. package/dist/src/grounding/feedback.js +276 -0
  109. package/dist/src/grounding/index.d.ts +123 -0
  110. package/dist/src/grounding/index.js +224 -0
  111. package/dist/src/grounding/verifier.d.ts +149 -0
  112. package/dist/src/grounding/verifier.js +484 -0
  113. package/dist/src/healing/detector.d.ts +110 -0
  114. package/dist/src/healing/detector.js +436 -0
  115. package/dist/src/healing/fixer.d.ts +138 -0
  116. package/dist/src/healing/fixer.js +572 -0
  117. package/dist/src/healing/index.d.ts +23 -0
  118. package/dist/src/healing/index.js +43 -0
  119. package/dist/src/hooks/index.d.ts +135 -0
  120. package/dist/src/hooks/index.js +317 -0
  121. package/dist/src/index.d.ts +23 -0
  122. package/dist/src/index.js +1266 -0
  123. package/dist/src/kernel/index.d.ts +155 -0
  124. package/dist/src/kernel/index.js +795 -0
  125. package/dist/src/kernel/invariants.d.ts +153 -0
  126. package/dist/src/kernel/invariants.js +355 -0
  127. package/dist/src/kernel/test-kernel.d.ts +6 -0
  128. package/dist/src/kernel/test-kernel.js +108 -0
  129. package/dist/src/kernel/test-real-mcp.d.ts +10 -0
  130. package/dist/src/kernel/test-real-mcp.js +295 -0
  131. package/dist/src/llm/index.d.ts +146 -0
  132. package/dist/src/llm/index.js +428 -0
  133. package/dist/src/llm/router.d.ts +136 -0
  134. package/dist/src/llm/router.js +510 -0
  135. package/dist/src/mcp/index.d.ts +85 -0
  136. package/dist/src/mcp/index.js +657 -0
  137. package/dist/src/mcp/resilient.d.ts +139 -0
  138. package/dist/src/mcp/resilient.js +417 -0
  139. package/dist/src/memory/cache.d.ts +118 -0
  140. package/dist/src/memory/cache.js +356 -0
  141. package/dist/src/memory/cognitive-workspace.d.ts +231 -0
  142. package/dist/src/memory/cognitive-workspace.js +521 -0
  143. package/dist/src/memory/consolidation.d.ts +99 -0
  144. package/dist/src/memory/consolidation.js +443 -0
  145. package/dist/src/memory/episodic.d.ts +114 -0
  146. package/dist/src/memory/episodic.js +394 -0
  147. package/dist/src/memory/forgetting.d.ts +134 -0
  148. package/dist/src/memory/forgetting.js +324 -0
  149. package/dist/src/memory/index.d.ts +211 -0
  150. package/dist/src/memory/index.js +367 -0
  151. package/dist/src/memory/indexer.d.ts +123 -0
  152. package/dist/src/memory/indexer.js +479 -0
  153. package/dist/src/memory/procedural.d.ts +136 -0
  154. package/dist/src/memory/procedural.js +479 -0
  155. package/dist/src/memory/semantic.d.ts +132 -0
  156. package/dist/src/memory/semantic.js +497 -0
  157. package/dist/src/memory/types.d.ts +193 -0
  158. package/dist/src/memory/types.js +15 -0
  159. package/dist/src/orchestrator.d.ts +65 -0
  160. package/dist/src/orchestrator.js +317 -0
  161. package/dist/src/persistence/index.d.ts +257 -0
  162. package/dist/src/persistence/index.js +763 -0
  163. package/dist/src/pipeline/executor.d.ts +51 -0
  164. package/dist/src/pipeline/executor.js +695 -0
  165. package/dist/src/pipeline/index.d.ts +7 -0
  166. package/dist/src/pipeline/index.js +11 -0
  167. package/dist/src/self-production.d.ts +67 -0
  168. package/dist/src/self-production.js +205 -0
  169. package/dist/src/subagents/executor.d.ts +58 -0
  170. package/dist/src/subagents/executor.js +283 -0
  171. package/dist/src/subagents/index.d.ts +37 -0
  172. package/dist/src/subagents/index.js +53 -0
  173. package/dist/src/subagents/registry.d.ts +23 -0
  174. package/dist/src/subagents/registry.js +167 -0
  175. package/dist/src/subagents/types.d.ts +79 -0
  176. package/dist/src/subagents/types.js +14 -0
  177. package/dist/src/tools/bash.d.ts +139 -0
  178. package/dist/src/tools/bash.js +583 -0
  179. package/dist/src/tools/edit.d.ts +125 -0
  180. package/dist/src/tools/edit.js +424 -0
  181. package/dist/src/tools/git.d.ts +179 -0
  182. package/dist/src/tools/git.js +504 -0
  183. package/dist/src/tools/index.d.ts +21 -0
  184. package/dist/src/tools/index.js +163 -0
  185. package/dist/src/types.d.ts +145 -0
  186. package/dist/src/types.js +7 -0
  187. package/dist/src/world-model/decoder.d.ts +163 -0
  188. package/dist/src/world-model/decoder.js +517 -0
  189. package/dist/src/world-model/digital-twin.d.ts +219 -0
  190. package/dist/src/world-model/digital-twin.js +695 -0
  191. package/dist/src/world-model/encoder.d.ts +141 -0
  192. package/dist/src/world-model/encoder.js +564 -0
  193. package/dist/src/world-model/index.d.ts +221 -0
  194. package/dist/src/world-model/index.js +772 -0
  195. package/dist/src/world-model/predictor.d.ts +161 -0
  196. package/dist/src/world-model/predictor.js +681 -0
  197. package/dist/src/world-model/test-value-jepa.d.ts +8 -0
  198. package/dist/src/world-model/test-value-jepa.js +430 -0
  199. package/dist/src/world-model/types.d.ts +341 -0
  200. package/dist/src/world-model/types.js +69 -0
  201. package/dist/src/world-model/value-jepa.d.ts +247 -0
  202. package/dist/src/world-model/value-jepa.js +622 -0
  203. package/dist/test/brain.test.d.ts +11 -0
  204. package/dist/test/brain.test.js +358 -0
  205. package/dist/test/cli/dispatcher.test.d.ts +4 -0
  206. package/dist/test/cli/dispatcher.test.js +332 -0
  207. package/dist/test/cli/human-loop.test.d.ts +4 -0
  208. package/dist/test/cli/human-loop.test.js +270 -0
  209. package/dist/test/grounding/feedback.test.d.ts +4 -0
  210. package/dist/test/grounding/feedback.test.js +462 -0
  211. package/dist/test/grounding/verifier.test.d.ts +4 -0
  212. package/dist/test/grounding/verifier.test.js +442 -0
  213. package/dist/test/grounding.test.d.ts +6 -0
  214. package/dist/test/grounding.test.js +246 -0
  215. package/dist/test/healing/detector.test.d.ts +4 -0
  216. package/dist/test/healing/detector.test.js +266 -0
  217. package/dist/test/healing/fixer.test.d.ts +4 -0
  218. package/dist/test/healing/fixer.test.js +369 -0
  219. package/dist/test/integration.test.d.ts +5 -0
  220. package/dist/test/integration.test.js +290 -0
  221. package/dist/test/tools/bash.test.d.ts +4 -0
  222. package/dist/test/tools/bash.test.js +348 -0
  223. package/dist/test/tools/edit.test.d.ts +4 -0
  224. package/dist/test/tools/edit.test.js +350 -0
  225. package/dist/test/tools/git.test.d.ts +4 -0
  226. package/dist/test/tools/git.test.js +350 -0
  227. package/package.json +60 -0
@@ -0,0 +1,332 @@
1
+ "use strict";
2
+ /**
3
+ * Tests for Genesis Tool Dispatcher
4
+ */
5
+ var __importDefault = (this && this.__importDefault) || function (mod) {
6
+ return (mod && mod.__esModule) ? mod : { "default": mod };
7
+ };
8
+ Object.defineProperty(exports, "__esModule", { value: true });
9
+ const node_test_1 = require("node:test");
10
+ const node_assert_1 = __importDefault(require("node:assert"));
11
+ const dispatcher_js_1 = require("../../src/cli/dispatcher.js");
12
+ (0, node_test_1.describe)('ToolDispatcher', () => {
13
+ (0, node_test_1.beforeEach)(() => {
14
+ (0, dispatcher_js_1.resetDispatcher)();
15
+ });
16
+ // ==========================================================================
17
+ // Parsing Tests
18
+ // ==========================================================================
19
+ (0, node_test_1.describe)('Parsing', () => {
20
+ (0, node_test_1.it)('should parse OpenAI-style tool calls', () => {
21
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
22
+ const llmCalls = [
23
+ {
24
+ id: 'call_1',
25
+ type: 'function',
26
+ function: {
27
+ name: 'bash',
28
+ arguments: '{"command": "ls -la"}',
29
+ },
30
+ },
31
+ {
32
+ id: 'call_2',
33
+ type: 'function',
34
+ function: {
35
+ name: 'edit',
36
+ arguments: '{"file_path": "test.ts", "old_string": "foo", "new_string": "bar"}',
37
+ },
38
+ },
39
+ ];
40
+ const calls = dispatcher.parseToolCalls(llmCalls);
41
+ node_assert_1.default.strictEqual(calls.length, 2);
42
+ node_assert_1.default.strictEqual(calls[0].name, 'bash');
43
+ node_assert_1.default.strictEqual(calls[0].params.command, 'ls -la');
44
+ node_assert_1.default.strictEqual(calls[1].name, 'edit');
45
+ node_assert_1.default.strictEqual(calls[1].params.file_path, 'test.ts');
46
+ });
47
+ (0, node_test_1.it)('should parse XML-style tool calls', () => {
48
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
49
+ const text = `
50
+ Let me run a command for you.
51
+ <tool_use name="bash">
52
+ <param name="command">echo "hello"</param>
53
+ </tool_use>
54
+ `;
55
+ const calls = dispatcher.parseToolCalls(text);
56
+ node_assert_1.default.strictEqual(calls.length, 1);
57
+ node_assert_1.default.strictEqual(calls[0].name, 'bash');
58
+ node_assert_1.default.strictEqual(calls[0].params.command, 'echo "hello"');
59
+ });
60
+ (0, node_test_1.it)('should parse invoke-style tool calls', () => {
61
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
62
+ const text = `
63
+ <invoke name="git_status">
64
+ <param name="cwd">/tmp</param>
65
+ </invoke>
66
+ `;
67
+ const calls = dispatcher.parseToolCalls(text);
68
+ node_assert_1.default.strictEqual(calls.length, 1);
69
+ node_assert_1.default.strictEqual(calls[0].name, 'git_status');
70
+ node_assert_1.default.strictEqual(calls[0].params.cwd, '/tmp');
71
+ });
72
+ (0, node_test_1.it)('should parse JSON-style tool calls', () => {
73
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
74
+ const text = `
75
+ I'll run this tool:
76
+ {"tool": "bash", "params": {"command": "pwd"}}
77
+ `;
78
+ const calls = dispatcher.parseToolCalls(text);
79
+ node_assert_1.default.strictEqual(calls.length, 1);
80
+ node_assert_1.default.strictEqual(calls[0].name, 'bash');
81
+ node_assert_1.default.strictEqual(calls[0].params.command, 'pwd');
82
+ });
83
+ (0, node_test_1.it)('should handle multiple tool calls in one response', () => {
84
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
85
+ const text = `
86
+ <tool_use name="bash">
87
+ <param name="command">ls</param>
88
+ </tool_use>
89
+ <tool_use name="bash">
90
+ <param name="command">pwd</param>
91
+ </tool_use>
92
+ `;
93
+ const calls = dispatcher.parseToolCalls(text);
94
+ node_assert_1.default.strictEqual(calls.length, 2);
95
+ });
96
+ (0, node_test_1.it)('should handle empty response', () => {
97
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
98
+ const calls = dispatcher.parseToolCalls('Just a plain response with no tools.');
99
+ node_assert_1.default.strictEqual(calls.length, 0);
100
+ });
101
+ (0, node_test_1.it)('should handle malformed tool calls gracefully', () => {
102
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
103
+ const text = `
104
+ <tool_use name="bash">
105
+ invalid xml content without params
106
+ </tool_use>
107
+ `;
108
+ // Should not throw
109
+ const calls = dispatcher.parseToolCalls(text);
110
+ node_assert_1.default.ok(Array.isArray(calls));
111
+ });
112
+ });
113
+ // ==========================================================================
114
+ // Routing Tests
115
+ // ==========================================================================
116
+ (0, node_test_1.describe)('Routing', () => {
117
+ (0, node_test_1.it)('should route local tools correctly', () => {
118
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
119
+ const calls = dispatcher.parseToolCalls([
120
+ {
121
+ id: 'call_1',
122
+ type: 'function',
123
+ function: { name: 'bash', arguments: '{}' },
124
+ },
125
+ {
126
+ id: 'call_2',
127
+ type: 'function',
128
+ function: { name: 'edit', arguments: '{}' },
129
+ },
130
+ {
131
+ id: 'call_3',
132
+ type: 'function',
133
+ function: { name: 'git_status', arguments: '{}' },
134
+ },
135
+ ]);
136
+ node_assert_1.default.strictEqual(calls[0].source, 'local');
137
+ node_assert_1.default.strictEqual(calls[1].source, 'local');
138
+ node_assert_1.default.strictEqual(calls[2].source, 'local');
139
+ });
140
+ (0, node_test_1.it)('should route MCP tools correctly', () => {
141
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
142
+ const calls = dispatcher.parseToolCalls([
143
+ {
144
+ id: 'call_1',
145
+ type: 'function',
146
+ function: { name: 'search_arxiv', arguments: '{}' },
147
+ },
148
+ {
149
+ id: 'call_2',
150
+ type: 'function',
151
+ function: { name: 'wolfram_query', arguments: '{}' },
152
+ },
153
+ ]);
154
+ node_assert_1.default.strictEqual(calls[0].source, 'mcp');
155
+ node_assert_1.default.strictEqual(calls[0].mcpServer, 'arxiv');
156
+ node_assert_1.default.strictEqual(calls[1].source, 'mcp');
157
+ node_assert_1.default.strictEqual(calls[1].mcpServer, 'wolfram');
158
+ });
159
+ (0, node_test_1.it)('should default unknown tools to local', () => {
160
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
161
+ const calls = dispatcher.parseToolCalls([
162
+ {
163
+ id: 'call_1',
164
+ type: 'function',
165
+ function: { name: 'unknown_tool', arguments: '{}' },
166
+ },
167
+ ]);
168
+ node_assert_1.default.strictEqual(calls[0].source, 'local');
169
+ });
170
+ });
171
+ // ==========================================================================
172
+ // Execution Tests
173
+ // ==========================================================================
174
+ (0, node_test_1.describe)('Execution', () => {
175
+ (0, node_test_1.it)('should execute local tools successfully', async () => {
176
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
177
+ const calls = [
178
+ {
179
+ id: 'call_1',
180
+ name: 'bash',
181
+ params: { command: 'echo "test"' },
182
+ source: 'local',
183
+ },
184
+ ];
185
+ const result = await dispatcher.dispatch(calls);
186
+ node_assert_1.default.ok(result.results.length > 0);
187
+ node_assert_1.default.strictEqual(result.results[0].name, 'bash');
188
+ // May or may not succeed depending on sandbox
189
+ });
190
+ (0, node_test_1.it)('should handle failed validation', async () => {
191
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
192
+ const calls = [
193
+ {
194
+ id: 'call_1',
195
+ name: 'edit',
196
+ params: {}, // Missing required params
197
+ source: 'local',
198
+ },
199
+ ];
200
+ const result = await dispatcher.dispatch(calls);
201
+ node_assert_1.default.strictEqual(result.results[0].success, false);
202
+ node_assert_1.default.ok(result.results[0].error);
203
+ });
204
+ (0, node_test_1.it)('should handle unknown tools gracefully', async () => {
205
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
206
+ const calls = [
207
+ {
208
+ id: 'call_1',
209
+ name: 'nonexistent_tool',
210
+ params: {},
211
+ source: 'local',
212
+ },
213
+ ];
214
+ const result = await dispatcher.dispatch(calls);
215
+ node_assert_1.default.strictEqual(result.results[0].success, false);
216
+ node_assert_1.default.ok(result.results[0].error?.includes('Unknown tool'));
217
+ });
218
+ (0, node_test_1.it)('should track execution duration', async () => {
219
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
220
+ const calls = [
221
+ {
222
+ id: 'call_1',
223
+ name: 'bash',
224
+ params: { command: 'echo "test"' },
225
+ source: 'local',
226
+ },
227
+ ];
228
+ const result = await dispatcher.dispatch(calls);
229
+ node_assert_1.default.ok(result.totalDuration >= 0);
230
+ node_assert_1.default.ok(result.results[0].duration >= 0);
231
+ });
232
+ (0, node_test_1.it)('should support parallel execution', async () => {
233
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)({ maxParallel: 3 });
234
+ const calls = [
235
+ { id: 'call_1', name: 'bash', params: { command: 'echo 1' }, source: 'local' },
236
+ { id: 'call_2', name: 'bash', params: { command: 'echo 2' }, source: 'local' },
237
+ { id: 'call_3', name: 'bash', params: { command: 'echo 3' }, source: 'local' },
238
+ ];
239
+ const result = await dispatcher.dispatch(calls);
240
+ node_assert_1.default.strictEqual(result.results.length, 3);
241
+ node_assert_1.default.ok(result.parallelExecutions >= 1);
242
+ });
243
+ });
244
+ // ==========================================================================
245
+ // History Tests
246
+ // ==========================================================================
247
+ (0, node_test_1.describe)('History', () => {
248
+ (0, node_test_1.it)('should track execution history', async () => {
249
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
250
+ await dispatcher.dispatch([
251
+ { id: 'call_1', name: 'bash', params: { command: 'echo 1' }, source: 'local' },
252
+ ]);
253
+ await dispatcher.dispatch([
254
+ { id: 'call_2', name: 'bash', params: { command: 'echo 2' }, source: 'local' },
255
+ ]);
256
+ const history = dispatcher.getHistory();
257
+ node_assert_1.default.strictEqual(history.length, 2);
258
+ });
259
+ (0, node_test_1.it)('should clear history', async () => {
260
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
261
+ await dispatcher.dispatch([
262
+ { id: 'call_1', name: 'bash', params: { command: 'echo 1' }, source: 'local' },
263
+ ]);
264
+ dispatcher.clearHistory();
265
+ node_assert_1.default.strictEqual(dispatcher.getHistory().length, 0);
266
+ });
267
+ });
268
+ // ==========================================================================
269
+ // Formatting Tests
270
+ // ==========================================================================
271
+ (0, node_test_1.describe)('Formatting', () => {
272
+ (0, node_test_1.it)('should format results for LLM context', async () => {
273
+ const dispatcher = (0, dispatcher_js_1.getDispatcher)();
274
+ const result = await dispatcher.dispatch([
275
+ { id: 'call_1', name: 'bash', params: { command: 'echo "hello"' }, source: 'local' },
276
+ ]);
277
+ const formatted = dispatcher.formatResultsForLLM(result.results);
278
+ node_assert_1.default.ok(formatted.includes('<tool_results>'));
279
+ node_assert_1.default.ok(formatted.includes('</tool_results>'));
280
+ node_assert_1.default.ok(formatted.includes('name="bash"'));
281
+ });
282
+ });
283
+ // ==========================================================================
284
+ // Tool Listing Tests
285
+ // ==========================================================================
286
+ (0, node_test_1.describe)('Tool Listing', () => {
287
+ (0, node_test_1.it)('should list available tools', () => {
288
+ const tools = (0, dispatcher_js_1.listAllTools)();
289
+ node_assert_1.default.ok(tools.local.includes('bash'));
290
+ node_assert_1.default.ok(tools.local.includes('edit'));
291
+ node_assert_1.default.ok(Object.keys(tools.mcp).includes('arxiv'));
292
+ });
293
+ });
294
+ // ==========================================================================
295
+ // Convenience Functions
296
+ // ==========================================================================
297
+ (0, node_test_1.describe)('Convenience Functions', () => {
298
+ (0, node_test_1.it)('dispatchTools should work with string input', async () => {
299
+ const text = `
300
+ <tool_use name="bash">
301
+ <param name="command">echo test</param>
302
+ </tool_use>
303
+ `;
304
+ const result = await (0, dispatcher_js_1.dispatchTools)(text);
305
+ node_assert_1.default.ok(result.results.length > 0);
306
+ });
307
+ (0, node_test_1.it)('executeTool should work', async () => {
308
+ const result = await (0, dispatcher_js_1.executeTool)('bash', { command: 'echo "hello"' });
309
+ node_assert_1.default.strictEqual(result.name, 'bash');
310
+ // Success depends on sandbox config
311
+ });
312
+ });
313
+ // ==========================================================================
314
+ // Progress Callback Tests
315
+ // ==========================================================================
316
+ (0, node_test_1.describe)('Progress Callback', () => {
317
+ (0, node_test_1.it)('should call progress callback', async () => {
318
+ const progressCalls = [];
319
+ const dispatcher = new dispatcher_js_1.ToolDispatcher({
320
+ onProgress: (status) => {
321
+ progressCalls.push(status.phase);
322
+ },
323
+ });
324
+ await dispatcher.dispatch([
325
+ { id: 'call_1', name: 'bash', params: { command: 'echo 1' }, source: 'local' },
326
+ ]);
327
+ node_assert_1.default.ok(progressCalls.includes('validating'));
328
+ node_assert_1.default.ok(progressCalls.includes('executing'));
329
+ node_assert_1.default.ok(progressCalls.includes('complete'));
330
+ });
331
+ });
332
+ });
@@ -0,0 +1,4 @@
1
+ /**
2
+ * Tests for Genesis Human-in-the-Loop Module
3
+ */
4
+ export {};
@@ -0,0 +1,270 @@
1
+ "use strict";
2
+ /**
3
+ * Tests for Genesis Human-in-the-Loop Module
4
+ */
5
+ var __importDefault = (this && this.__importDefault) || function (mod) {
6
+ return (mod && mod.__esModule) ? mod : { "default": mod };
7
+ };
8
+ Object.defineProperty(exports, "__esModule", { value: true });
9
+ const node_test_1 = require("node:test");
10
+ const node_assert_1 = __importDefault(require("node:assert"));
11
+ const human_loop_js_1 = require("../../src/cli/human-loop.js");
12
+ const index_js_1 = require("../../src/tools/index.js");
13
+ (0, node_test_1.describe)('HumanLoop', () => {
14
+ (0, node_test_1.beforeEach)(() => {
15
+ (0, human_loop_js_1.resetHumanLoop)();
16
+ });
17
+ // ==========================================================================
18
+ // Configuration Tests
19
+ // ==========================================================================
20
+ (0, node_test_1.describe)('Configuration', () => {
21
+ (0, node_test_1.it)('should use default configuration', () => {
22
+ const hl = new human_loop_js_1.HumanLoop();
23
+ node_assert_1.default.ok(hl);
24
+ });
25
+ (0, node_test_1.it)('should accept custom configuration', () => {
26
+ const hl = new human_loop_js_1.HumanLoop({
27
+ defaultTimeout: 5000,
28
+ allowSkip: false,
29
+ useColors: false,
30
+ });
31
+ node_assert_1.default.ok(hl);
32
+ });
33
+ });
34
+ // ==========================================================================
35
+ // Question Types
36
+ // ==========================================================================
37
+ (0, node_test_1.describe)('Question Types', () => {
38
+ (0, node_test_1.it)('should support confirm type', () => {
39
+ const question = {
40
+ type: 'confirm',
41
+ text: 'Do you want to proceed?',
42
+ default: true,
43
+ };
44
+ node_assert_1.default.strictEqual(question.type, 'confirm');
45
+ node_assert_1.default.strictEqual(question.default, true);
46
+ });
47
+ (0, node_test_1.it)('should support choice type with options', () => {
48
+ const options = [
49
+ { value: 'a', label: 'Option A', description: 'First option' },
50
+ { value: 'b', label: 'Option B', recommended: true },
51
+ { value: 'c', label: 'Option C' },
52
+ ];
53
+ const question = {
54
+ type: 'choice',
55
+ text: 'Choose one:',
56
+ options,
57
+ };
58
+ node_assert_1.default.strictEqual(question.options?.length, 3);
59
+ node_assert_1.default.ok(question.options?.[1].recommended);
60
+ });
61
+ (0, node_test_1.it)('should support multiChoice type', () => {
62
+ const question = {
63
+ type: 'multiChoice',
64
+ text: 'Select all that apply:',
65
+ options: [
66
+ { value: '1', label: 'One' },
67
+ { value: '2', label: 'Two' },
68
+ { value: '3', label: 'Three' },
69
+ ],
70
+ };
71
+ node_assert_1.default.strictEqual(question.type, 'multiChoice');
72
+ });
73
+ (0, node_test_1.it)('should support text type', () => {
74
+ const question = {
75
+ type: 'text',
76
+ text: 'Enter your name:',
77
+ default: 'Anonymous',
78
+ };
79
+ node_assert_1.default.strictEqual(question.type, 'text');
80
+ node_assert_1.default.strictEqual(question.default, 'Anonymous');
81
+ });
82
+ (0, node_test_1.it)('should support context', () => {
83
+ const question = {
84
+ type: 'confirm',
85
+ text: 'Proceed?',
86
+ context: 'This will delete 10 files.',
87
+ };
88
+ node_assert_1.default.strictEqual(question.context, 'This will delete 10 files.');
89
+ });
90
+ });
91
+ // ==========================================================================
92
+ // History & Stats
93
+ // ==========================================================================
94
+ (0, node_test_1.describe)('History & Stats', () => {
95
+ (0, node_test_1.it)('should track empty history initially', () => {
96
+ const hl = new human_loop_js_1.HumanLoop();
97
+ const history = hl.getHistory();
98
+ node_assert_1.default.strictEqual(history.length, 0);
99
+ });
100
+ (0, node_test_1.it)('should clear history', () => {
101
+ const hl = new human_loop_js_1.HumanLoop();
102
+ hl.clearHistory();
103
+ const history = hl.getHistory();
104
+ node_assert_1.default.strictEqual(history.length, 0);
105
+ });
106
+ (0, node_test_1.it)('should return stats', () => {
107
+ const hl = new human_loop_js_1.HumanLoop();
108
+ const stats = hl.stats();
109
+ node_assert_1.default.strictEqual(stats.totalQuestions, 0);
110
+ node_assert_1.default.strictEqual(stats.responded, 0);
111
+ node_assert_1.default.strictEqual(stats.timedOut, 0);
112
+ node_assert_1.default.strictEqual(stats.cancelled, 0);
113
+ node_assert_1.default.strictEqual(stats.avgResponseTime, 0);
114
+ });
115
+ });
116
+ // ==========================================================================
117
+ // Singleton Tests
118
+ // ==========================================================================
119
+ (0, node_test_1.describe)('Singleton', () => {
120
+ (0, node_test_1.it)('should return same instance', () => {
121
+ const hl1 = (0, human_loop_js_1.getHumanLoop)();
122
+ const hl2 = (0, human_loop_js_1.getHumanLoop)();
123
+ node_assert_1.default.strictEqual(hl1, hl2);
124
+ });
125
+ (0, node_test_1.it)('should reset singleton', () => {
126
+ const hl1 = (0, human_loop_js_1.getHumanLoop)();
127
+ (0, human_loop_js_1.resetHumanLoop)();
128
+ const hl2 = (0, human_loop_js_1.getHumanLoop)();
129
+ node_assert_1.default.notStrictEqual(hl1, hl2);
130
+ });
131
+ });
132
+ // ==========================================================================
133
+ // Tool Registration
134
+ // ==========================================================================
135
+ (0, node_test_1.describe)('Tool Registration', () => {
136
+ (0, node_test_1.it)('should register ask_user tool', () => {
137
+ const tool = index_js_1.toolRegistry.get('ask_user');
138
+ node_assert_1.default.ok(tool);
139
+ node_assert_1.default.strictEqual(tool.name, 'ask_user');
140
+ node_assert_1.default.ok(tool.description.includes('Ask the user'));
141
+ });
142
+ (0, node_test_1.it)('should register confirm tool', () => {
143
+ const tool = index_js_1.toolRegistry.get('confirm');
144
+ node_assert_1.default.ok(tool);
145
+ node_assert_1.default.strictEqual(tool.name, 'confirm');
146
+ });
147
+ (0, node_test_1.it)('ask_user should validate params', () => {
148
+ const tool = index_js_1.toolRegistry.get('ask_user');
149
+ // Missing text
150
+ const invalid = tool?.validate?.({});
151
+ node_assert_1.default.strictEqual(invalid?.valid, false);
152
+ // Valid
153
+ const valid = tool?.validate?.({ text: 'Question?' });
154
+ node_assert_1.default.strictEqual(valid?.valid, true);
155
+ });
156
+ });
157
+ // ==========================================================================
158
+ // Question Option Tests
159
+ // ==========================================================================
160
+ (0, node_test_1.describe)('Question Options', () => {
161
+ (0, node_test_1.it)('should support recommended option', () => {
162
+ const options = [
163
+ { value: 'safe', label: 'Safe approach', recommended: true },
164
+ { value: 'fast', label: 'Fast approach' },
165
+ ];
166
+ const recommended = options.find(o => o.recommended);
167
+ node_assert_1.default.ok(recommended);
168
+ node_assert_1.default.strictEqual(recommended.value, 'safe');
169
+ });
170
+ (0, node_test_1.it)('should support option descriptions', () => {
171
+ const options = [
172
+ { value: 'a', label: 'A', description: 'This is option A' },
173
+ { value: 'b', label: 'B', description: 'This is option B' },
174
+ ];
175
+ node_assert_1.default.strictEqual(options[0].description, 'This is option A');
176
+ });
177
+ });
178
+ // ==========================================================================
179
+ // Answer Structure Tests
180
+ // ==========================================================================
181
+ (0, node_test_1.describe)('Answer Structure', () => {
182
+ (0, node_test_1.it)('should have correct answer structure', () => {
183
+ // Simulated answer
184
+ const answer = {
185
+ question: {
186
+ type: 'confirm',
187
+ text: 'Test?',
188
+ },
189
+ value: true,
190
+ responded: true,
191
+ responseTime: 1500,
192
+ };
193
+ node_assert_1.default.strictEqual(answer.value, true);
194
+ node_assert_1.default.strictEqual(answer.responded, true);
195
+ node_assert_1.default.ok(answer.responseTime >= 0);
196
+ });
197
+ (0, node_test_1.it)('should track timeout', () => {
198
+ const answer = {
199
+ question: { type: 'confirm', text: 'Test?' },
200
+ value: false,
201
+ responded: false,
202
+ timedOut: true,
203
+ responseTime: 5000,
204
+ };
205
+ node_assert_1.default.strictEqual(answer.timedOut, true);
206
+ node_assert_1.default.strictEqual(answer.responded, false);
207
+ });
208
+ (0, node_test_1.it)('should track cancellation', () => {
209
+ const answer = {
210
+ question: { type: 'choice', text: 'Choose?' },
211
+ value: '',
212
+ responded: true,
213
+ cancelled: true,
214
+ responseTime: 500,
215
+ };
216
+ node_assert_1.default.strictEqual(answer.cancelled, true);
217
+ node_assert_1.default.strictEqual(answer.value, '');
218
+ });
219
+ });
220
+ // ==========================================================================
221
+ // Integration Tests (mocked)
222
+ // ==========================================================================
223
+ (0, node_test_1.describe)('Integration', () => {
224
+ (0, node_test_1.it)('should support callback on response', () => {
225
+ let callbackCalled = false;
226
+ const hl = new human_loop_js_1.HumanLoop({
227
+ onResponse: (answer) => {
228
+ callbackCalled = true;
229
+ },
230
+ });
231
+ // We can't actually test interactive input here,
232
+ // but we can verify the callback is set up correctly
233
+ node_assert_1.default.ok(hl);
234
+ });
235
+ (0, node_test_1.it)('should close cleanly', () => {
236
+ const hl = new human_loop_js_1.HumanLoop();
237
+ hl.close();
238
+ // Should not throw
239
+ node_assert_1.default.ok(true);
240
+ });
241
+ });
242
+ // ==========================================================================
243
+ // Destructive Operation Tests
244
+ // ==========================================================================
245
+ (0, node_test_1.describe)('Destructive Operations', () => {
246
+ (0, node_test_1.it)('should format destructive warning', () => {
247
+ // This tests the structure of destructive confirmations
248
+ const operation = 'Delete all files';
249
+ const details = '10 files will be permanently removed';
250
+ // Just verify the strings are valid
251
+ node_assert_1.default.ok(operation.length > 0);
252
+ node_assert_1.default.ok(details.length > 0);
253
+ });
254
+ });
255
+ // ==========================================================================
256
+ // Approach Selection Tests
257
+ // ==========================================================================
258
+ (0, node_test_1.describe)('Approach Selection', () => {
259
+ (0, node_test_1.it)('should format approach options', () => {
260
+ const task = 'Implement authentication';
261
+ const approaches = [
262
+ { name: 'JWT', description: 'Token-based auth', recommended: true },
263
+ { name: 'Session', description: 'Server-side sessions' },
264
+ { name: 'OAuth', description: 'Third-party providers' },
265
+ ];
266
+ node_assert_1.default.strictEqual(approaches.length, 3);
267
+ node_assert_1.default.ok(approaches.find(a => a.recommended));
268
+ });
269
+ });
270
+ });
@@ -0,0 +1,4 @@
1
+ /**
2
+ * Tests for Genesis Grounding Feedback Loop
3
+ */
4
+ export {};