@weavelogic/knowledge-graph-agent 0.3.0 → 0.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (149) hide show
  1. package/README.md +290 -3
  2. package/dist/_virtual/index10.js +2 -2
  3. package/dist/_virtual/index6.js +2 -2
  4. package/dist/_virtual/index7.js +2 -2
  5. package/dist/_virtual/index8.js +2 -2
  6. package/dist/_virtual/index9.js +2 -2
  7. package/dist/audit/config.d.ts +150 -0
  8. package/dist/audit/config.d.ts.map +1 -0
  9. package/dist/audit/config.js +111 -0
  10. package/dist/audit/config.js.map +1 -0
  11. package/dist/audit/index.d.ts +38 -0
  12. package/dist/audit/index.d.ts.map +1 -0
  13. package/dist/audit/services/audit-chain.d.ts +276 -0
  14. package/dist/audit/services/audit-chain.d.ts.map +1 -0
  15. package/dist/audit/services/audit-chain.js +502 -0
  16. package/dist/audit/services/audit-chain.js.map +1 -0
  17. package/dist/audit/services/index.d.ts +11 -0
  18. package/dist/audit/services/index.d.ts.map +1 -0
  19. package/dist/audit/services/syndication.d.ts +334 -0
  20. package/dist/audit/services/syndication.d.ts.map +1 -0
  21. package/dist/audit/services/syndication.js +589 -0
  22. package/dist/audit/services/syndication.js.map +1 -0
  23. package/dist/audit/types.d.ts +453 -0
  24. package/dist/audit/types.d.ts.map +1 -0
  25. package/dist/cli/commands/audit.d.ts +21 -0
  26. package/dist/cli/commands/audit.d.ts.map +1 -0
  27. package/dist/cli/commands/audit.js +621 -0
  28. package/dist/cli/commands/audit.js.map +1 -0
  29. package/dist/cli/commands/vector.d.ts +14 -0
  30. package/dist/cli/commands/vector.d.ts.map +1 -0
  31. package/dist/cli/commands/vector.js +429 -0
  32. package/dist/cli/commands/vector.js.map +1 -0
  33. package/dist/cli/commands/workflow.d.ts +12 -0
  34. package/dist/cli/commands/workflow.d.ts.map +1 -0
  35. package/dist/cli/commands/workflow.js +471 -0
  36. package/dist/cli/commands/workflow.js.map +1 -0
  37. package/dist/cli/index.d.ts.map +1 -1
  38. package/dist/cli/index.js +26 -0
  39. package/dist/cli/index.js.map +1 -1
  40. package/dist/database/schemas/index.d.ts +85 -0
  41. package/dist/database/schemas/index.d.ts.map +1 -0
  42. package/dist/index.d.ts +2 -0
  43. package/dist/index.d.ts.map +1 -1
  44. package/dist/index.js +9 -0
  45. package/dist/index.js.map +1 -1
  46. package/dist/mcp-server/tools/audit/checkpoint.d.ts +58 -0
  47. package/dist/mcp-server/tools/audit/checkpoint.d.ts.map +1 -0
  48. package/dist/mcp-server/tools/audit/checkpoint.js +73 -0
  49. package/dist/mcp-server/tools/audit/checkpoint.js.map +1 -0
  50. package/dist/mcp-server/tools/audit/index.d.ts +53 -0
  51. package/dist/mcp-server/tools/audit/index.d.ts.map +1 -0
  52. package/dist/mcp-server/tools/audit/index.js +12 -0
  53. package/dist/mcp-server/tools/audit/index.js.map +1 -0
  54. package/dist/mcp-server/tools/audit/query.d.ts +58 -0
  55. package/dist/mcp-server/tools/audit/query.d.ts.map +1 -0
  56. package/dist/mcp-server/tools/audit/query.js +125 -0
  57. package/dist/mcp-server/tools/audit/query.js.map +1 -0
  58. package/dist/mcp-server/tools/audit/sync.d.ts +58 -0
  59. package/dist/mcp-server/tools/audit/sync.d.ts.map +1 -0
  60. package/dist/mcp-server/tools/audit/sync.js +126 -0
  61. package/dist/mcp-server/tools/audit/sync.js.map +1 -0
  62. package/dist/mcp-server/tools/index.d.ts +3 -0
  63. package/dist/mcp-server/tools/index.d.ts.map +1 -1
  64. package/dist/mcp-server/tools/registry.js +90 -0
  65. package/dist/mcp-server/tools/registry.js.map +1 -1
  66. package/dist/mcp-server/tools/vector/index.d.ts +12 -0
  67. package/dist/mcp-server/tools/vector/index.d.ts.map +1 -0
  68. package/dist/mcp-server/tools/vector/index.js +12 -0
  69. package/dist/mcp-server/tools/vector/index.js.map +1 -0
  70. package/dist/mcp-server/tools/vector/search.d.ts +41 -0
  71. package/dist/mcp-server/tools/vector/search.d.ts.map +1 -0
  72. package/dist/mcp-server/tools/vector/search.js +224 -0
  73. package/dist/mcp-server/tools/vector/search.js.map +1 -0
  74. package/dist/mcp-server/tools/vector/trajectory.d.ts +39 -0
  75. package/dist/mcp-server/tools/vector/trajectory.d.ts.map +1 -0
  76. package/dist/mcp-server/tools/vector/trajectory.js +170 -0
  77. package/dist/mcp-server/tools/vector/trajectory.js.map +1 -0
  78. package/dist/mcp-server/tools/vector/upsert.d.ts +44 -0
  79. package/dist/mcp-server/tools/vector/upsert.d.ts.map +1 -0
  80. package/dist/mcp-server/tools/vector/upsert.js +175 -0
  81. package/dist/mcp-server/tools/vector/upsert.js.map +1 -0
  82. package/dist/mcp-server/tools/workflow/index.d.ts +29 -0
  83. package/dist/mcp-server/tools/workflow/index.d.ts.map +1 -0
  84. package/dist/mcp-server/tools/workflow/index.js +12 -0
  85. package/dist/mcp-server/tools/workflow/index.js.map +1 -0
  86. package/dist/mcp-server/tools/workflow/list.d.ts +41 -0
  87. package/dist/mcp-server/tools/workflow/list.d.ts.map +1 -0
  88. package/dist/mcp-server/tools/workflow/list.js +195 -0
  89. package/dist/mcp-server/tools/workflow/list.js.map +1 -0
  90. package/dist/mcp-server/tools/workflow/start.d.ts +40 -0
  91. package/dist/mcp-server/tools/workflow/start.d.ts.map +1 -0
  92. package/dist/mcp-server/tools/workflow/start.js +165 -0
  93. package/dist/mcp-server/tools/workflow/start.js.map +1 -0
  94. package/dist/mcp-server/tools/workflow/status.d.ts +38 -0
  95. package/dist/mcp-server/tools/workflow/status.d.ts.map +1 -0
  96. package/dist/mcp-server/tools/workflow/status.js +97 -0
  97. package/dist/mcp-server/tools/workflow/status.js.map +1 -0
  98. package/dist/node_modules/ajv/dist/compile/index.js +1 -1
  99. package/dist/node_modules/ajv/dist/vocabularies/applicator/index.js +1 -1
  100. package/dist/node_modules/ajv/dist/vocabularies/core/index.js +1 -1
  101. package/dist/node_modules/ajv/dist/vocabularies/format/index.js +1 -1
  102. package/dist/node_modules/ajv/dist/vocabularies/validation/index.js +1 -1
  103. package/dist/vector/config.d.ts +300 -0
  104. package/dist/vector/config.d.ts.map +1 -0
  105. package/dist/vector/config.js +124 -0
  106. package/dist/vector/config.js.map +1 -0
  107. package/dist/vector/index.d.ts +50 -0
  108. package/dist/vector/index.d.ts.map +1 -0
  109. package/dist/vector/services/index.d.ts +13 -0
  110. package/dist/vector/services/index.d.ts.map +1 -0
  111. package/dist/vector/services/trajectory-tracker.d.ts +405 -0
  112. package/dist/vector/services/trajectory-tracker.d.ts.map +1 -0
  113. package/dist/vector/services/trajectory-tracker.js +445 -0
  114. package/dist/vector/services/trajectory-tracker.js.map +1 -0
  115. package/dist/vector/services/vector-store.d.ts +339 -0
  116. package/dist/vector/services/vector-store.d.ts.map +1 -0
  117. package/dist/vector/services/vector-store.js +748 -0
  118. package/dist/vector/services/vector-store.js.map +1 -0
  119. package/dist/vector/types.d.ts +677 -0
  120. package/dist/vector/types.d.ts.map +1 -0
  121. package/dist/workflow/adapters/goap-adapter.d.ts +196 -0
  122. package/dist/workflow/adapters/goap-adapter.d.ts.map +1 -0
  123. package/dist/workflow/adapters/goap-adapter.js +706 -0
  124. package/dist/workflow/adapters/goap-adapter.js.map +1 -0
  125. package/dist/workflow/adapters/index.d.ts +10 -0
  126. package/dist/workflow/adapters/index.d.ts.map +1 -0
  127. package/dist/workflow/config.d.ts +135 -0
  128. package/dist/workflow/config.d.ts.map +1 -0
  129. package/dist/workflow/config.js +92 -0
  130. package/dist/workflow/config.js.map +1 -0
  131. package/dist/workflow/handlers/index.d.ts +9 -0
  132. package/dist/workflow/handlers/index.d.ts.map +1 -0
  133. package/dist/workflow/handlers/webhook-handlers.d.ts +397 -0
  134. package/dist/workflow/handlers/webhook-handlers.d.ts.map +1 -0
  135. package/dist/workflow/handlers/webhook-handlers.js +454 -0
  136. package/dist/workflow/handlers/webhook-handlers.js.map +1 -0
  137. package/dist/workflow/index.d.ts +42 -0
  138. package/dist/workflow/index.d.ts.map +1 -0
  139. package/dist/workflow/services/index.d.ts +9 -0
  140. package/dist/workflow/services/index.d.ts.map +1 -0
  141. package/dist/workflow/services/workflow-service.d.ts +318 -0
  142. package/dist/workflow/services/workflow-service.d.ts.map +1 -0
  143. package/dist/workflow/services/workflow-service.js +577 -0
  144. package/dist/workflow/services/workflow-service.js.map +1 -0
  145. package/dist/workflow/types.d.ts +470 -0
  146. package/dist/workflow/types.d.ts.map +1 -0
  147. package/dist/workflow/workflows/realtime-collab.d.ts +245 -0
  148. package/dist/workflow/workflows/realtime-collab.d.ts.map +1 -0
  149. package/package.json +1 -1
@@ -0,0 +1,706 @@
1
+ import { createLogger } from "../../utils/logger.js";
2
+ const logger = createLogger("goap-adapter");
3
+ class PriorityQueue {
4
+ items = [];
5
+ /**
6
+ * Add an item to the queue with a priority
7
+ *
8
+ * @param item - The item to add
9
+ * @param priority - Priority value (lower = higher priority)
10
+ */
11
+ enqueue(item, priority) {
12
+ this.items.push({ item, priority });
13
+ this.bubbleUp(this.items.length - 1);
14
+ }
15
+ /**
16
+ * Remove and return the highest priority item
17
+ *
18
+ * @returns The item with lowest priority value, or undefined if empty
19
+ */
20
+ dequeue() {
21
+ if (this.items.length === 0) {
22
+ return void 0;
23
+ }
24
+ const result = this.items[0].item;
25
+ if (this.items.length === 1) {
26
+ this.items.pop();
27
+ } else {
28
+ this.items[0] = this.items.pop();
29
+ this.bubbleDown(0);
30
+ }
31
+ return result;
32
+ }
33
+ /**
34
+ * Check if the queue is empty
35
+ */
36
+ isEmpty() {
37
+ return this.items.length === 0;
38
+ }
39
+ /**
40
+ * Get the current size of the queue
41
+ */
42
+ size() {
43
+ return this.items.length;
44
+ }
45
+ /**
46
+ * Peek at the highest priority item without removing it
47
+ */
48
+ peek() {
49
+ return this.items[0]?.item;
50
+ }
51
+ /**
52
+ * Clear all items from the queue
53
+ */
54
+ clear() {
55
+ this.items = [];
56
+ }
57
+ /**
58
+ * Bubble up an item to maintain heap property
59
+ */
60
+ bubbleUp(index) {
61
+ while (index > 0) {
62
+ const parentIndex = Math.floor((index - 1) / 2);
63
+ if (this.items[parentIndex].priority <= this.items[index].priority) {
64
+ break;
65
+ }
66
+ [this.items[parentIndex], this.items[index]] = [
67
+ this.items[index],
68
+ this.items[parentIndex]
69
+ ];
70
+ index = parentIndex;
71
+ }
72
+ }
73
+ /**
74
+ * Bubble down an item to maintain heap property
75
+ */
76
+ bubbleDown(index) {
77
+ const length = this.items.length;
78
+ while (true) {
79
+ const leftChild = 2 * index + 1;
80
+ const rightChild = 2 * index + 2;
81
+ let smallest = index;
82
+ if (leftChild < length && this.items[leftChild].priority < this.items[smallest].priority) {
83
+ smallest = leftChild;
84
+ }
85
+ if (rightChild < length && this.items[rightChild].priority < this.items[smallest].priority) {
86
+ smallest = rightChild;
87
+ }
88
+ if (smallest === index) {
89
+ break;
90
+ }
91
+ [this.items[index], this.items[smallest]] = [
92
+ this.items[smallest],
93
+ this.items[index]
94
+ ];
95
+ index = smallest;
96
+ }
97
+ }
98
+ }
99
+ class GOAPAdapter {
100
+ config;
101
+ actions = /* @__PURE__ */ new Map();
102
+ goals = /* @__PURE__ */ new Map();
103
+ planCache = /* @__PURE__ */ new Map();
104
+ customHeuristic;
105
+ constructor(config = {}) {
106
+ this.config = {
107
+ maxIterations: config.maxIterations ?? 1e3,
108
+ timeoutMs: config.timeoutMs ?? 3e4,
109
+ defaultCost: config.defaultCost ?? 1,
110
+ enableCaching: config.enableCaching ?? true,
111
+ maxPlanLength: config.maxPlanLength ?? 20
112
+ };
113
+ this.customHeuristic = config.heuristic;
114
+ this.registerDefaultActions();
115
+ if (config.actions) {
116
+ for (const action of config.actions) {
117
+ this.registerAction(action);
118
+ }
119
+ }
120
+ this.registerDefaultGoals();
121
+ }
122
+ /**
123
+ * Register default actions for documentation workflows
124
+ */
125
+ registerDefaultActions() {
126
+ this.registerAction({
127
+ id: "analyze-spec",
128
+ name: "Analyze Specification",
129
+ description: "Analyze the specification document for completeness",
130
+ cost: 1,
131
+ preconditions: {
132
+ hasSpecification: true
133
+ },
134
+ effects: {
135
+ specCompleteness: 0.5
136
+ // Will be refined during execution
137
+ }
138
+ });
139
+ this.registerAction({
140
+ id: "generate-acceptance-criteria",
141
+ name: "Generate Acceptance Criteria",
142
+ description: "Generate acceptance criteria from specification",
143
+ cost: 2,
144
+ preconditions: {
145
+ hasSpecification: true,
146
+ specCompleteness: 0.5
147
+ },
148
+ effects: {
149
+ hasAcceptanceCriteria: true
150
+ }
151
+ });
152
+ this.registerAction({
153
+ id: "create-task",
154
+ name: "Create Task",
155
+ description: "Create a development task from the specification",
156
+ cost: 1,
157
+ preconditions: {
158
+ hasSpecification: true,
159
+ hasAcceptanceCriteria: true,
160
+ blockersFree: true
161
+ },
162
+ effects: {
163
+ taskDefined: true
164
+ }
165
+ });
166
+ this.registerAction({
167
+ id: "start-development",
168
+ name: "Start Development",
169
+ description: "Begin development work on the task",
170
+ cost: 3,
171
+ preconditions: {
172
+ taskDefined: true,
173
+ blockersFree: true
174
+ },
175
+ effects: {
176
+ developmentStarted: true
177
+ }
178
+ });
179
+ this.registerAction({
180
+ id: "fill-gaps",
181
+ name: "Fill Documentation Gaps",
182
+ description: "Generate content to fill documentation gaps",
183
+ cost: 2,
184
+ preconditions: {
185
+ hasSpecification: true
186
+ },
187
+ effects: {
188
+ specCompleteness: 0.8,
189
+ pendingGaps: []
190
+ }
191
+ });
192
+ this.registerAction({
193
+ id: "resolve-blockers",
194
+ name: "Resolve Blockers",
195
+ description: "Resolve blocking issues",
196
+ cost: 4,
197
+ preconditions: {
198
+ blockersFree: false
199
+ },
200
+ effects: {
201
+ blockersFree: true
202
+ }
203
+ });
204
+ }
205
+ /**
206
+ * Register default goals
207
+ */
208
+ registerDefaultGoals() {
209
+ this.registerGoal({
210
+ id: "start-development",
211
+ name: "Start Development",
212
+ description: "Get the project ready to begin development",
213
+ conditions: {
214
+ taskDefined: true,
215
+ developmentStarted: true
216
+ },
217
+ priority: 10
218
+ });
219
+ this.registerGoal({
220
+ id: "complete-spec",
221
+ name: "Complete Specification",
222
+ description: "Ensure specification is complete with acceptance criteria",
223
+ conditions: {
224
+ hasSpecification: true,
225
+ specCompleteness: 0.8,
226
+ hasAcceptanceCriteria: true
227
+ },
228
+ priority: 8
229
+ });
230
+ this.registerGoal({
231
+ id: "resolve-blockers",
232
+ name: "Resolve All Blockers",
233
+ description: "Clear all blocking issues",
234
+ conditions: {
235
+ blockersFree: true
236
+ },
237
+ priority: 9
238
+ });
239
+ }
240
+ /**
241
+ * Register an action
242
+ *
243
+ * @param action - Action definition to register
244
+ */
245
+ registerAction(action) {
246
+ this.actions.set(action.id, action);
247
+ logger.debug("Registered action", { actionId: action.id });
248
+ }
249
+ /**
250
+ * Register a goal
251
+ *
252
+ * @param goal - Goal definition to register
253
+ */
254
+ registerGoal(goal) {
255
+ this.goals.set(goal.id, goal);
256
+ logger.debug("Registered goal", { goalId: goal.id });
257
+ }
258
+ /**
259
+ * Get a registered action by ID
260
+ *
261
+ * @param actionId - Action identifier
262
+ * @returns Action definition or undefined
263
+ */
264
+ getAction(actionId) {
265
+ return this.actions.get(actionId);
266
+ }
267
+ /**
268
+ * Get a registered goal by ID
269
+ *
270
+ * @param goalId - Goal identifier
271
+ * @returns Goal definition or undefined
272
+ */
273
+ getGoal(goalId) {
274
+ return this.goals.get(goalId);
275
+ }
276
+ /**
277
+ * Get all registered actions
278
+ *
279
+ * @returns Array of action definitions
280
+ */
281
+ getActions() {
282
+ return Array.from(this.actions.values());
283
+ }
284
+ /**
285
+ * Get all registered goals
286
+ *
287
+ * @returns Array of goal definitions
288
+ */
289
+ getGoals() {
290
+ return Array.from(this.goals.values());
291
+ }
292
+ /**
293
+ * Create a plan to achieve a goal from the current state
294
+ *
295
+ * @param currentState - Current world state
296
+ * @param goalId - Goal to achieve
297
+ * @returns Plan to achieve the goal
298
+ */
299
+ createPlan(currentState, goalId) {
300
+ const goal = this.goals.get(goalId);
301
+ if (!goal) {
302
+ return {
303
+ goalId,
304
+ actionIds: [],
305
+ totalCost: Infinity,
306
+ achievable: false,
307
+ reason: `Unknown goal: ${goalId}`,
308
+ createdAt: /* @__PURE__ */ new Date()
309
+ };
310
+ }
311
+ const cacheKey = this.createCacheKey(currentState, goalId);
312
+ if (this.config.enableCaching && this.planCache.has(cacheKey)) {
313
+ const cached = this.planCache.get(cacheKey);
314
+ logger.debug("Using cached plan", { goalId, cacheKey });
315
+ return cached;
316
+ }
317
+ logger.debug("Creating plan", { goalId, currentState });
318
+ if (this.isGoalSatisfied(currentState, goal)) {
319
+ const plan2 = {
320
+ goalId,
321
+ actionIds: [],
322
+ totalCost: 0,
323
+ achievable: true,
324
+ createdAt: /* @__PURE__ */ new Date()
325
+ };
326
+ this.cachePlan(cacheKey, plan2);
327
+ return plan2;
328
+ }
329
+ const plan = this.aStarSearch(currentState, goal);
330
+ this.cachePlan(cacheKey, plan);
331
+ return plan;
332
+ }
333
+ /**
334
+ * A* search algorithm for plan finding
335
+ *
336
+ * Uses a binary heap priority queue for efficient O(log n) operations.
337
+ * Implements proper path reconstruction using parent node references.
338
+ */
339
+ aStarSearch(startState, goal) {
340
+ const startTime = Date.now();
341
+ const openSet = new PriorityQueue();
342
+ const closedSet = /* @__PURE__ */ new Set();
343
+ const startHeuristic = this.heuristic(startState, goal);
344
+ const startNode = {
345
+ state: { ...startState },
346
+ gCost: 0,
347
+ hCost: startHeuristic,
348
+ fCost: startHeuristic,
349
+ parent: null,
350
+ action: null
351
+ };
352
+ openSet.enqueue(startNode, startNode.fCost);
353
+ let iterations = 0;
354
+ let nodesExplored = 0;
355
+ while (!openSet.isEmpty() && iterations < this.config.maxIterations) {
356
+ if (Date.now() - startTime > this.config.timeoutMs) {
357
+ logger.warn("Planning timeout", { goalId: goal.id, iterations, nodesExplored });
358
+ return {
359
+ goalId: goal.id,
360
+ actionIds: [],
361
+ totalCost: Infinity,
362
+ achievable: false,
363
+ reason: "Planning timeout exceeded",
364
+ createdAt: /* @__PURE__ */ new Date()
365
+ };
366
+ }
367
+ iterations++;
368
+ const current = openSet.dequeue();
369
+ const stateKey = this.stateToKey(current.state);
370
+ if (closedSet.has(stateKey)) {
371
+ continue;
372
+ }
373
+ closedSet.add(stateKey);
374
+ nodesExplored++;
375
+ if (this.isGoalSatisfied(current.state, goal)) {
376
+ const plan = this.reconstructPlan(current, goal);
377
+ logger.debug("Plan found", {
378
+ goalId: goal.id,
379
+ iterations,
380
+ nodesExplored,
381
+ actionCount: plan.actionIds.length
382
+ });
383
+ return plan;
384
+ }
385
+ let pathLength = 0;
386
+ let node = current;
387
+ while (node) {
388
+ pathLength++;
389
+ node = node.parent;
390
+ }
391
+ if (pathLength >= this.config.maxPlanLength) {
392
+ continue;
393
+ }
394
+ for (const action of Array.from(this.actions.values())) {
395
+ if (!this.canApply(action, current.state)) {
396
+ continue;
397
+ }
398
+ const newState = this.applyAction(action, current.state);
399
+ const newStateKey = this.stateToKey(newState);
400
+ if (closedSet.has(newStateKey)) {
401
+ continue;
402
+ }
403
+ const gCost = current.gCost + action.cost;
404
+ const hCost = this.heuristic(newState, goal);
405
+ const fCost = gCost + hCost;
406
+ const newNode = {
407
+ state: newState,
408
+ gCost,
409
+ hCost,
410
+ fCost,
411
+ parent: current,
412
+ action
413
+ };
414
+ openSet.enqueue(newNode, fCost);
415
+ }
416
+ }
417
+ logger.debug("No plan found", { goalId: goal.id, iterations, nodesExplored });
418
+ return {
419
+ goalId: goal.id,
420
+ actionIds: [],
421
+ totalCost: Infinity,
422
+ achievable: false,
423
+ reason: "No valid action sequence found",
424
+ createdAt: /* @__PURE__ */ new Date()
425
+ };
426
+ }
427
+ /**
428
+ * Reconstruct the plan from the goal node by following parent references
429
+ *
430
+ * @param goalNode - The node that reached the goal
431
+ * @param goal - The goal definition
432
+ * @returns Complete GOAP plan
433
+ */
434
+ reconstructPlan(goalNode, goal) {
435
+ const actionIds = [];
436
+ let current = goalNode;
437
+ let totalCost = 0;
438
+ while (current && current.action) {
439
+ actionIds.unshift(current.action.id);
440
+ totalCost += current.action.cost;
441
+ current = current.parent;
442
+ }
443
+ const lengthPenalty = actionIds.length * 0.05;
444
+ const costPenalty = totalCost * 0.01;
445
+ const confidence = Math.max(0.3, 1 - lengthPenalty - costPenalty);
446
+ return {
447
+ goalId: goal.id,
448
+ actionIds,
449
+ totalCost,
450
+ achievable: true,
451
+ estimatedTimeMs: totalCost * 1e3,
452
+ createdAt: /* @__PURE__ */ new Date(),
453
+ confidence
454
+ };
455
+ }
456
+ /**
457
+ * Heuristic function for A* (estimates cost to goal)
458
+ *
459
+ * Uses Manhattan-like distance for numeric values and
460
+ * fixed penalties for boolean mismatches.
461
+ *
462
+ * @param state - Current world state
463
+ * @param goal - Goal to reach
464
+ * @returns Estimated cost to reach goal
465
+ */
466
+ heuristic(state, goal) {
467
+ if (this.customHeuristic) {
468
+ return this.customHeuristic(state, goal.conditions);
469
+ }
470
+ let distance = 0;
471
+ for (const [key, value] of Object.entries(goal.conditions)) {
472
+ const currentValue = state[key];
473
+ if (typeof value === "boolean") {
474
+ if (currentValue !== value) {
475
+ distance += 5;
476
+ }
477
+ } else if (typeof value === "number" && typeof currentValue === "number") {
478
+ if (currentValue < value) {
479
+ distance += (value - currentValue) * 10;
480
+ }
481
+ } else if (Array.isArray(value) && Array.isArray(currentValue)) {
482
+ if (value.length === 0 && currentValue.length > 0) {
483
+ distance += currentValue.length * 2;
484
+ }
485
+ } else if (currentValue !== value) {
486
+ distance += this.config.defaultCost;
487
+ }
488
+ }
489
+ return distance;
490
+ }
491
+ /**
492
+ * Check if a goal is satisfied by the current state
493
+ */
494
+ isGoalSatisfied(state, goal) {
495
+ for (const [key, value] of Object.entries(goal.conditions)) {
496
+ const currentValue = state[key];
497
+ if (typeof value === "number" && typeof currentValue === "number") {
498
+ if (currentValue < value) {
499
+ return false;
500
+ }
501
+ } else if (Array.isArray(value) && Array.isArray(currentValue)) {
502
+ if (value.length > 0 && currentValue.length > 0) {
503
+ return false;
504
+ }
505
+ } else if (currentValue !== value) {
506
+ return false;
507
+ }
508
+ }
509
+ return true;
510
+ }
511
+ /**
512
+ * Check if an action can be applied to a state
513
+ */
514
+ canApply(action, state) {
515
+ for (const [key, value] of Object.entries(action.preconditions)) {
516
+ const currentValue = state[key];
517
+ if (typeof value === "number" && typeof currentValue === "number") {
518
+ if (currentValue < value) {
519
+ return false;
520
+ }
521
+ } else if (currentValue !== value) {
522
+ return false;
523
+ }
524
+ }
525
+ return true;
526
+ }
527
+ /**
528
+ * Apply an action to a state and return the new state
529
+ */
530
+ applyAction(action, state) {
531
+ const newState = { ...state };
532
+ for (const [key, value] of Object.entries(action.effects)) {
533
+ newState[key] = value;
534
+ }
535
+ return newState;
536
+ }
537
+ /**
538
+ * Convert state to a cache key string
539
+ */
540
+ stateToKey(state) {
541
+ const sortedKeys = Object.keys(state).sort();
542
+ const values = sortedKeys.map((k) => `${k}:${JSON.stringify(state[k])}`);
543
+ return values.join("|");
544
+ }
545
+ /**
546
+ * Create cache key for a plan
547
+ */
548
+ createCacheKey(state, goalId) {
549
+ return `${goalId}::${this.stateToKey(state)}`;
550
+ }
551
+ /**
552
+ * Cache a plan
553
+ */
554
+ cachePlan(key, plan) {
555
+ if (this.config.enableCaching) {
556
+ this.planCache.set(key, plan);
557
+ }
558
+ }
559
+ /**
560
+ * Clear the plan cache
561
+ */
562
+ clearCache() {
563
+ this.planCache.clear();
564
+ logger.debug("Plan cache cleared");
565
+ }
566
+ /**
567
+ * Execute a plan
568
+ *
569
+ * @param plan - Plan to execute
570
+ * @param initialState - Initial world state
571
+ * @returns Execution result
572
+ */
573
+ async executePlan(plan, initialState) {
574
+ if (!plan.achievable) {
575
+ return {
576
+ success: false,
577
+ finalState: initialState,
578
+ completedSteps: [],
579
+ error: plan.reason || "Plan is not achievable",
580
+ executionTimeMs: 0
581
+ };
582
+ }
583
+ const startTime = Date.now();
584
+ let currentState = { ...initialState };
585
+ const completedSteps = [];
586
+ logger.info("Executing plan", {
587
+ goalId: plan.goalId,
588
+ actionCount: plan.actionIds.length
589
+ });
590
+ for (const actionId of plan.actionIds) {
591
+ const action = this.actions.get(actionId);
592
+ if (!action) {
593
+ return {
594
+ success: false,
595
+ finalState: currentState,
596
+ completedSteps,
597
+ failedStep: actionId,
598
+ error: `Unknown action: ${actionId}`,
599
+ executionTimeMs: Date.now() - startTime
600
+ };
601
+ }
602
+ if (!this.canApply(action, currentState)) {
603
+ return {
604
+ success: false,
605
+ finalState: currentState,
606
+ completedSteps,
607
+ failedStep: actionId,
608
+ error: `Preconditions not met for action: ${actionId}`,
609
+ executionTimeMs: Date.now() - startTime
610
+ };
611
+ }
612
+ try {
613
+ if (action.execute) {
614
+ currentState = await action.execute(currentState);
615
+ } else {
616
+ currentState = this.applyAction(action, currentState);
617
+ }
618
+ completedSteps.push(actionId);
619
+ logger.debug(`Action completed: ${actionId}`);
620
+ } catch (error) {
621
+ logger.error(`Action failed: ${actionId}`, error instanceof Error ? error : new Error(String(error)));
622
+ return {
623
+ success: false,
624
+ finalState: currentState,
625
+ completedSteps,
626
+ failedStep: actionId,
627
+ error: error instanceof Error ? error.message : String(error),
628
+ executionTimeMs: Date.now() - startTime
629
+ };
630
+ }
631
+ }
632
+ logger.info("Plan execution completed", {
633
+ goalId: plan.goalId,
634
+ completedSteps: completedSteps.length
635
+ });
636
+ return {
637
+ success: true,
638
+ finalState: currentState,
639
+ completedSteps,
640
+ executionTimeMs: Date.now() - startTime
641
+ };
642
+ }
643
+ /**
644
+ * Evaluate readiness for development
645
+ *
646
+ * @param state - Current world state
647
+ * @returns Readiness evaluation
648
+ */
649
+ evaluateReadiness(state) {
650
+ const blockers = [];
651
+ const recommendations = [];
652
+ let score = 0;
653
+ if (!state.hasSpecification) {
654
+ blockers.push("No specification document found");
655
+ recommendations.push("Create a specification document");
656
+ } else {
657
+ score += 0.2;
658
+ if (state.specCompleteness < 0.5) {
659
+ blockers.push("Specification is incomplete");
660
+ recommendations.push("Complete the specification document");
661
+ } else if (state.specCompleteness < 0.8) {
662
+ recommendations.push("Consider improving specification completeness");
663
+ score += 0.1;
664
+ } else {
665
+ score += 0.2;
666
+ }
667
+ }
668
+ if (!state.hasAcceptanceCriteria) {
669
+ blockers.push("No acceptance criteria defined");
670
+ recommendations.push("Define acceptance criteria");
671
+ } else {
672
+ score += 0.2;
673
+ }
674
+ if (!state.blockersFree) {
675
+ blockers.push("Blocking issues exist");
676
+ recommendations.push("Resolve blocking issues");
677
+ } else {
678
+ score += 0.2;
679
+ }
680
+ if (state.pendingGaps.length > 0) {
681
+ recommendations.push(`Address ${state.pendingGaps.length} documentation gaps`);
682
+ } else {
683
+ score += 0.1;
684
+ }
685
+ if (state.taskDefined) {
686
+ score += 0.1;
687
+ } else if (blockers.length === 0) {
688
+ recommendations.push("Create a task from the specification");
689
+ }
690
+ return {
691
+ score: Math.min(1, score),
692
+ ready: blockers.length === 0 && score >= 0.7,
693
+ blockers,
694
+ recommendations,
695
+ evaluatedAt: /* @__PURE__ */ new Date()
696
+ };
697
+ }
698
+ }
699
+ function createGOAPAdapter(config) {
700
+ return new GOAPAdapter(config);
701
+ }
702
+ export {
703
+ GOAPAdapter,
704
+ createGOAPAdapter
705
+ };
706
+ //# sourceMappingURL=goap-adapter.js.map