@tenex-chat/backend 0.9.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 (427) hide show
  1. package/README.md +194 -0
  2. package/dist/backend-wrapper.cjs +3 -0
  3. package/dist/src/index.js +331928 -0
  4. package/package.json +103 -0
  5. package/src/agents/AgentRegistry.ts +418 -0
  6. package/src/agents/AgentStorage.ts +1133 -0
  7. package/src/agents/ConfigResolver.ts +229 -0
  8. package/src/agents/agent-installer.ts +236 -0
  9. package/src/agents/agent-loader.ts +241 -0
  10. package/src/agents/constants.ts +82 -0
  11. package/src/agents/errors.ts +48 -0
  12. package/src/agents/execution/AgentExecutor.ts +561 -0
  13. package/src/agents/execution/ExecutionContextFactory.ts +112 -0
  14. package/src/agents/execution/MessageCompiler.ts +597 -0
  15. package/src/agents/execution/MessageSyncer.ts +100 -0
  16. package/src/agents/execution/PostCompletionChecker.ts +278 -0
  17. package/src/agents/execution/ProgressMonitor.ts +50 -0
  18. package/src/agents/execution/RALResolver.ts +177 -0
  19. package/src/agents/execution/SessionManager.ts +181 -0
  20. package/src/agents/execution/StreamCallbacks.ts +312 -0
  21. package/src/agents/execution/StreamExecutionHandler.ts +579 -0
  22. package/src/agents/execution/StreamSetup.ts +313 -0
  23. package/src/agents/execution/ToolEventHandlers.ts +239 -0
  24. package/src/agents/execution/ToolExecutionTracker.ts +498 -0
  25. package/src/agents/execution/ToolResultUtils.ts +97 -0
  26. package/src/agents/execution/ToolSupervisionWrapper.ts +174 -0
  27. package/src/agents/execution/constants.ts +16 -0
  28. package/src/agents/execution/index.ts +3 -0
  29. package/src/agents/execution/types.ts +96 -0
  30. package/src/agents/execution/utils.ts +26 -0
  31. package/src/agents/index.ts +4 -0
  32. package/src/agents/script-installer.ts +266 -0
  33. package/src/agents/supervision/SupervisorLLMService.ts +253 -0
  34. package/src/agents/supervision/SupervisorOrchestrator.ts +471 -0
  35. package/src/agents/supervision/heuristics/ConsecutiveToolsWithoutTodoHeuristic.ts +73 -0
  36. package/src/agents/supervision/heuristics/DelegationClaimHeuristic.ts +80 -0
  37. package/src/agents/supervision/heuristics/HeuristicRegistry.ts +114 -0
  38. package/src/agents/supervision/heuristics/PendingTodosHeuristic.ts +93 -0
  39. package/src/agents/supervision/heuristics/SilentAgentHeuristic.ts +54 -0
  40. package/src/agents/supervision/heuristics/index.ts +5 -0
  41. package/src/agents/supervision/index.ts +28 -0
  42. package/src/agents/supervision/registerHeuristics.ts +110 -0
  43. package/src/agents/supervision/supervisionHealthCheck.ts +123 -0
  44. package/src/agents/supervision/types.ts +171 -0
  45. package/src/agents/tool-names.ts +46 -0
  46. package/src/agents/tool-normalization.ts +184 -0
  47. package/src/agents/types/index.ts +2 -0
  48. package/src/agents/types/runtime.ts +74 -0
  49. package/src/agents/types/storage.ts +145 -0
  50. package/src/commands/agent/import/index.ts +6 -0
  51. package/src/commands/agent/import/openclaw-distiller.ts +57 -0
  52. package/src/commands/agent/import/openclaw-reader.ts +141 -0
  53. package/src/commands/agent/import/openclaw.ts +154 -0
  54. package/src/commands/agent/index.ts +6 -0
  55. package/src/commands/agent.ts +215 -0
  56. package/src/commands/daemon.ts +198 -0
  57. package/src/commands/doctor.ts +134 -0
  58. package/src/commands/setup/embed.ts +228 -0
  59. package/src/commands/setup/global-system-prompt.ts +223 -0
  60. package/src/commands/setup/image.ts +179 -0
  61. package/src/commands/setup/index.ts +16 -0
  62. package/src/commands/setup/interactive.ts +95 -0
  63. package/src/commands/setup/llm.ts +38 -0
  64. package/src/commands/setup/onboarding.ts +294 -0
  65. package/src/commands/setup/providers.ts +27 -0
  66. package/src/constants.ts +34 -0
  67. package/src/conversations/ConversationDiskReader.ts +148 -0
  68. package/src/conversations/ConversationRegistry.ts +728 -0
  69. package/src/conversations/ConversationStore.ts +868 -0
  70. package/src/conversations/MessageBuilder.ts +866 -0
  71. package/src/conversations/executionTime.ts +62 -0
  72. package/src/conversations/formatters/DelegationXmlFormatter.ts +64 -0
  73. package/src/conversations/formatters/ThreadedConversationFormatter.ts +303 -0
  74. package/src/conversations/formatters/index.ts +9 -0
  75. package/src/conversations/formatters/utils/MessageFormatter.ts +46 -0
  76. package/src/conversations/formatters/utils/TimestampFormatter.ts +56 -0
  77. package/src/conversations/formatters/utils/TreeBuilder.ts +131 -0
  78. package/src/conversations/formatters/utils/TreeRenderer.ts +49 -0
  79. package/src/conversations/index.ts +2 -0
  80. package/src/conversations/persistence/ToolMessageStorage.ts +143 -0
  81. package/src/conversations/search/ConversationIndexManager.ts +393 -0
  82. package/src/conversations/search/QueryParser.ts +114 -0
  83. package/src/conversations/search/SearchEngine.ts +175 -0
  84. package/src/conversations/search/SnippetExtractor.ts +345 -0
  85. package/src/conversations/search/embeddings/ConversationEmbeddingService.ts +484 -0
  86. package/src/conversations/search/embeddings/ConversationIndexingJob.ts +320 -0
  87. package/src/conversations/search/embeddings/IndexingStateManager.ts +338 -0
  88. package/src/conversations/search/embeddings/index.ts +18 -0
  89. package/src/conversations/search/index.ts +49 -0
  90. package/src/conversations/search/types.ts +124 -0
  91. package/src/conversations/services/CategoryManager.ts +160 -0
  92. package/src/conversations/services/ConversationResolver.ts +296 -0
  93. package/src/conversations/services/ConversationSummarizer.ts +234 -0
  94. package/src/conversations/services/MetadataDebounceManager.ts +188 -0
  95. package/src/conversations/services/index.ts +2 -0
  96. package/src/conversations/types.ts +148 -0
  97. package/src/conversations/utils/content-utils.ts +69 -0
  98. package/src/conversations/utils/image-placeholder.ts +281 -0
  99. package/src/conversations/utils/image-url-utils.ts +171 -0
  100. package/src/conversations/utils/multimodal-content.ts +90 -0
  101. package/src/conversations/utils/tool-result-truncator.ts +159 -0
  102. package/src/daemon/Daemon.ts +1883 -0
  103. package/src/daemon/ProjectRuntime.ts +657 -0
  104. package/src/daemon/RestartState.ts +152 -0
  105. package/src/daemon/RuntimeLifecycle.ts +268 -0
  106. package/src/daemon/SubscriptionManager.ts +305 -0
  107. package/src/daemon/UnixSocketTransport.ts +318 -0
  108. package/src/daemon/filters/SubscriptionFilterBuilder.ts +119 -0
  109. package/src/daemon/index.ts +9 -0
  110. package/src/daemon/routing/DaemonRouter.ts +491 -0
  111. package/src/daemon/types.ts +150 -0
  112. package/src/daemon/utils/routing-log.ts +76 -0
  113. package/src/daemon/utils/telemetry.ts +173 -0
  114. package/src/event-handler/agentDeletion.ts +383 -0
  115. package/src/event-handler/index.ts +749 -0
  116. package/src/event-handler/newConversation.ts +165 -0
  117. package/src/event-handler/project.ts +166 -0
  118. package/src/event-handler/reply.ts +18 -0
  119. package/src/events/NDKAgentDefinition.ts +292 -0
  120. package/src/events/NDKAgentLesson.ts +106 -0
  121. package/src/events/NDKEventMetadata.ts +34 -0
  122. package/src/events/NDKMCPTool.ts +60 -0
  123. package/src/events/NDKProjectStatus.ts +384 -0
  124. package/src/events/index.ts +4 -0
  125. package/src/index.ts +126 -0
  126. package/src/lib/agent-home.ts +334 -0
  127. package/src/lib/error-formatter.ts +200 -0
  128. package/src/lib/fs/filesystem.ts +128 -0
  129. package/src/lib/fs/index.ts +1 -0
  130. package/src/lib/json-parser.ts +30 -0
  131. package/src/lib/string.ts +15 -0
  132. package/src/lib/time.ts +74 -0
  133. package/src/llm/ChunkHandler.ts +277 -0
  134. package/src/llm/FinishHandler.ts +250 -0
  135. package/src/llm/LLMConfigEditor.ts +154 -0
  136. package/src/llm/LLMServiceFactory.ts +230 -0
  137. package/src/llm/MessageProcessor.ts +90 -0
  138. package/src/llm/RecordingState.ts +37 -0
  139. package/src/llm/StreamPublisher.ts +40 -0
  140. package/src/llm/TracingUtils.ts +77 -0
  141. package/src/llm/chunk-validators.ts +57 -0
  142. package/src/llm/constants.ts +6 -0
  143. package/src/llm/index.ts +12 -0
  144. package/src/llm/meta/MetaModelResolver.ts +352 -0
  145. package/src/llm/meta/index.ts +11 -0
  146. package/src/llm/middleware/flight-recorder.ts +188 -0
  147. package/src/llm/providers/MockProvider.ts +332 -0
  148. package/src/llm/providers/agent/ClaudeCodeProvider.ts +343 -0
  149. package/src/llm/providers/agent/ClaudeCodeToolsAdapter.ts +203 -0
  150. package/src/llm/providers/agent/CodexAppServerProvider.ts +214 -0
  151. package/src/llm/providers/agent/CodexAppServerToolsAdapter.ts +91 -0
  152. package/src/llm/providers/agent/index.ts +10 -0
  153. package/src/llm/providers/base/AgentProvider.ts +107 -0
  154. package/src/llm/providers/base/BaseProvider.ts +114 -0
  155. package/src/llm/providers/base/StandardProvider.ts +38 -0
  156. package/src/llm/providers/base/index.ts +9 -0
  157. package/src/llm/providers/index.ts +106 -0
  158. package/src/llm/providers/key-manager.ts +238 -0
  159. package/src/llm/providers/ollama-models.ts +105 -0
  160. package/src/llm/providers/openrouter-models.ts +102 -0
  161. package/src/llm/providers/provider-ids.ts +18 -0
  162. package/src/llm/providers/registry/ProviderRegistry.ts +414 -0
  163. package/src/llm/providers/registry/index.ts +7 -0
  164. package/src/llm/providers/standard/AnthropicProvider.ts +71 -0
  165. package/src/llm/providers/standard/OllamaProvider.ts +59 -0
  166. package/src/llm/providers/standard/OpenAIProvider.ts +44 -0
  167. package/src/llm/providers/standard/OpenRouterProvider.ts +103 -0
  168. package/src/llm/providers/standard/index.ts +10 -0
  169. package/src/llm/providers/types.ts +194 -0
  170. package/src/llm/providers/usage-metadata.ts +78 -0
  171. package/src/llm/service.ts +713 -0
  172. package/src/llm/types.ts +167 -0
  173. package/src/llm/utils/ConfigurationManager.ts +650 -0
  174. package/src/llm/utils/ConfigurationTester.ts +229 -0
  175. package/src/llm/utils/ModelSelector.ts +212 -0
  176. package/src/llm/utils/ProviderConfigUI.ts +177 -0
  177. package/src/llm/utils/claudeCodePromptCompiler.ts +141 -0
  178. package/src/llm/utils/codex-models.ts +53 -0
  179. package/src/llm/utils/context-window-cache.ts +30 -0
  180. package/src/llm/utils/models-dev-cache.ts +267 -0
  181. package/src/llm/utils/provider-setup.ts +50 -0
  182. package/src/llm/utils/tool-errors.ts +78 -0
  183. package/src/llm/utils/usage.ts +74 -0
  184. package/src/logging/EventRoutingLogger.ts +205 -0
  185. package/src/nostr/AgentEventDecoder.ts +357 -0
  186. package/src/nostr/AgentEventEncoder.ts +677 -0
  187. package/src/nostr/AgentProfilePublisher.ts +657 -0
  188. package/src/nostr/AgentPublisher.ts +437 -0
  189. package/src/nostr/BlossomService.ts +226 -0
  190. package/src/nostr/InterventionPublisher.ts +132 -0
  191. package/src/nostr/TagExtractor.ts +228 -0
  192. package/src/nostr/collectEvents.ts +83 -0
  193. package/src/nostr/constants.ts +38 -0
  194. package/src/nostr/encryption.ts +26 -0
  195. package/src/nostr/index.ts +31 -0
  196. package/src/nostr/keys.ts +17 -0
  197. package/src/nostr/kinds.ts +37 -0
  198. package/src/nostr/ndkClient.ts +72 -0
  199. package/src/nostr/relays.ts +43 -0
  200. package/src/nostr/trace-context.ts +39 -0
  201. package/src/nostr/types.ts +227 -0
  202. package/src/nostr/utils.ts +84 -0
  203. package/src/prompts/core/FragmentRegistry.ts +30 -0
  204. package/src/prompts/core/PromptBuilder.ts +98 -0
  205. package/src/prompts/core/index.ts +3 -0
  206. package/src/prompts/core/types.ts +13 -0
  207. package/src/prompts/fragments/00-global-system-prompt.ts +44 -0
  208. package/src/prompts/fragments/01-agent-identity.ts +69 -0
  209. package/src/prompts/fragments/02-agent-home-directory.ts +114 -0
  210. package/src/prompts/fragments/03-system-reminders-explanation.ts +14 -0
  211. package/src/prompts/fragments/04-relay-configuration.ts +38 -0
  212. package/src/prompts/fragments/05-delegation-chain.ts +45 -0
  213. package/src/prompts/fragments/06-agent-todos.ts +74 -0
  214. package/src/prompts/fragments/06-todo-usage-guidance.ts +34 -0
  215. package/src/prompts/fragments/07-meta-project-context.ts +234 -0
  216. package/src/prompts/fragments/08-active-conversations.ts +382 -0
  217. package/src/prompts/fragments/09-recent-conversations.ts +153 -0
  218. package/src/prompts/fragments/10-referenced-article.ts +21 -0
  219. package/src/prompts/fragments/11-nudges.ts +134 -0
  220. package/src/prompts/fragments/12-skills.ts +127 -0
  221. package/src/prompts/fragments/13-available-nudges.ts +122 -0
  222. package/src/prompts/fragments/15-available-agents.ts +53 -0
  223. package/src/prompts/fragments/16-stay-in-your-lane.ts +41 -0
  224. package/src/prompts/fragments/17-todo-before-delegation.ts +39 -0
  225. package/src/prompts/fragments/20-voice-mode.ts +62 -0
  226. package/src/prompts/fragments/22-scheduled-tasks.ts +175 -0
  227. package/src/prompts/fragments/24-retrieved-lessons.ts +26 -0
  228. package/src/prompts/fragments/25-rag-instructions.ts +333 -0
  229. package/src/prompts/fragments/26-mcp-resources.ts +237 -0
  230. package/src/prompts/fragments/27-memorized-reports.ts +77 -0
  231. package/src/prompts/fragments/28-agent-directed-monitoring.ts +32 -0
  232. package/src/prompts/fragments/29-rag-collections.ts +50 -0
  233. package/src/prompts/fragments/30-worktree-context.ts +98 -0
  234. package/src/prompts/fragments/31-agents-md-guidance.ts +96 -0
  235. package/src/prompts/fragments/32-process-metrics.ts +72 -0
  236. package/src/prompts/fragments/debug-mode.ts +48 -0
  237. package/src/prompts/fragments/delegation-completion.ts +44 -0
  238. package/src/prompts/fragments/index.ts +91 -0
  239. package/src/prompts/index.ts +21 -0
  240. package/src/prompts/utils/systemPromptBuilder.ts +777 -0
  241. package/src/scripts/migrate-prefix-index.ts +157 -0
  242. package/src/services/AgentDefinitionMonitor.ts +701 -0
  243. package/src/services/ConfigService.ts +723 -0
  244. package/src/services/CooldownRegistry.ts +199 -0
  245. package/src/services/LLMOperationsRegistry.ts +424 -0
  246. package/src/services/OwnerAgentListService.ts +354 -0
  247. package/src/services/PubkeyService.ts +308 -0
  248. package/src/services/agents/AgentMetadataStore.ts +72 -0
  249. package/src/services/agents/AgentResolution.ts +59 -0
  250. package/src/services/agents/EscalationService.ts +281 -0
  251. package/src/services/agents/NDKAgentDiscovery.ts +95 -0
  252. package/src/services/agents/index.ts +7 -0
  253. package/src/services/agents-md/AgentsMdService.ts +184 -0
  254. package/src/services/agents-md/SystemReminderInjector.ts +238 -0
  255. package/src/services/agents-md/index.ts +11 -0
  256. package/src/services/apns/APNsClient.ts +203 -0
  257. package/src/services/apns/APNsService.ts +358 -0
  258. package/src/services/apns/index.ts +11 -0
  259. package/src/services/apns/types.ts +80 -0
  260. package/src/services/compression/CompressionService.ts +445 -0
  261. package/src/services/compression/compression-schema.ts +28 -0
  262. package/src/services/compression/compression-types.ts +74 -0
  263. package/src/services/compression/compression-utils.ts +587 -0
  264. package/src/services/config/types.ts +394 -0
  265. package/src/services/dispatch/AgentDispatchService.ts +937 -0
  266. package/src/services/dispatch/AgentRouter.ts +181 -0
  267. package/src/services/dispatch/DelegationCompletionHandler.ts +232 -0
  268. package/src/services/embedding/EmbeddingProvider.ts +188 -0
  269. package/src/services/embedding/index.ts +5 -0
  270. package/src/services/event-context/EventContextService.ts +108 -0
  271. package/src/services/event-context/index.ts +2 -0
  272. package/src/services/heuristics/ContextBuilder.ts +106 -0
  273. package/src/services/heuristics/HeuristicEngine.ts +200 -0
  274. package/src/services/heuristics/formatters.ts +58 -0
  275. package/src/services/heuristics/index.ts +12 -0
  276. package/src/services/heuristics/rules/index.ts +25 -0
  277. package/src/services/heuristics/rules/todoBeforeDelegation.ts +69 -0
  278. package/src/services/heuristics/rules/todoReminderOnToolUse.ts +63 -0
  279. package/src/services/heuristics/types.ts +144 -0
  280. package/src/services/image/ImageGenerationService.ts +389 -0
  281. package/src/services/image/index.ts +12 -0
  282. package/src/services/intervention/InterventionService.ts +1352 -0
  283. package/src/services/intervention/index.ts +7 -0
  284. package/src/services/mcp/MCPManager.ts +683 -0
  285. package/src/services/mcp/McpNotificationDelivery.ts +139 -0
  286. package/src/services/mcp/McpSubscriptionService.ts +653 -0
  287. package/src/services/mcp/mcpInstaller.ts +130 -0
  288. package/src/services/nip46/Nip46SigningLog.ts +81 -0
  289. package/src/services/nip46/Nip46SigningService.ts +467 -0
  290. package/src/services/nip46/index.ts +4 -0
  291. package/src/services/nudge/NudgeService.ts +224 -0
  292. package/src/services/nudge/NudgeWhitelistService.ts +382 -0
  293. package/src/services/nudge/index.ts +5 -0
  294. package/src/services/nudge/types.ts +83 -0
  295. package/src/services/projects/ProjectContext.ts +672 -0
  296. package/src/services/projects/ProjectContextStore.ts +102 -0
  297. package/src/services/projects/index.ts +6 -0
  298. package/src/services/prompt-compiler/index.ts +15 -0
  299. package/src/services/prompt-compiler/prompt-compiler-service.ts +1143 -0
  300. package/src/services/pubkey-gate/PubkeyGateService.ts +93 -0
  301. package/src/services/pubkey-gate/index.ts +1 -0
  302. package/src/services/rag/EmbeddingProviderFactory.ts +292 -0
  303. package/src/services/rag/LanceDBMaintenanceService.ts +211 -0
  304. package/src/services/rag/RAGDatabaseService.ts +173 -0
  305. package/src/services/rag/RAGOperations.ts +682 -0
  306. package/src/services/rag/RAGService.ts +240 -0
  307. package/src/services/rag/RagSubscriptionService.ts +618 -0
  308. package/src/services/rag/rag-utils.ts +174 -0
  309. package/src/services/ral/PendingDelegationsRegistry.ts +168 -0
  310. package/src/services/ral/RALRegistry.ts +2782 -0
  311. package/src/services/ral/index.ts +4 -0
  312. package/src/services/ral/types.ts +292 -0
  313. package/src/services/reports/LocalReportStore.ts +380 -0
  314. package/src/services/reports/ReportEmbeddingService.ts +430 -0
  315. package/src/services/reports/ReportService.ts +440 -0
  316. package/src/services/reports/articleUtils.ts +52 -0
  317. package/src/services/reports/index.ts +7 -0
  318. package/src/services/scheduling/SchedulerService.ts +1057 -0
  319. package/src/services/scheduling/errors.ts +14 -0
  320. package/src/services/scheduling/index.ts +7 -0
  321. package/src/services/scheduling/utils.ts +77 -0
  322. package/src/services/search/SearchProviderRegistry.ts +78 -0
  323. package/src/services/search/UnifiedSearchService.ts +218 -0
  324. package/src/services/search/index.ts +47 -0
  325. package/src/services/search/projectFilter.ts +22 -0
  326. package/src/services/search/providers/ConversationSearchProvider.ts +48 -0
  327. package/src/services/search/providers/LessonSearchProvider.ts +75 -0
  328. package/src/services/search/providers/ReportSearchProvider.ts +49 -0
  329. package/src/services/search/types.ts +144 -0
  330. package/src/services/skill/SkillService.ts +482 -0
  331. package/src/services/skill/index.ts +2 -0
  332. package/src/services/skill/types.ts +70 -0
  333. package/src/services/status/OperationsStatusService.ts +276 -0
  334. package/src/services/status/ProjectStatusService.ts +522 -0
  335. package/src/services/status/index.ts +11 -0
  336. package/src/services/storage/PrefixKVStore.ts +242 -0
  337. package/src/services/storage/index.ts +1 -0
  338. package/src/services/system-reminder/SystemReminderUtils.ts +96 -0
  339. package/src/services/system-reminder/index.ts +7 -0
  340. package/src/services/trust-pubkeys/TrustPubkeyService.ts +325 -0
  341. package/src/services/trust-pubkeys/index.ts +2 -0
  342. package/src/telemetry/ConversationSpanManager.ts +111 -0
  343. package/src/telemetry/EventLoopMonitor.ts +206 -0
  344. package/src/telemetry/LLMSpanRegistry.ts +20 -0
  345. package/src/telemetry/NostrSpanProcessor.ts +89 -0
  346. package/src/telemetry/ToolCallSpanProcessor.ts +66 -0
  347. package/src/telemetry/diagnostics.ts +27 -0
  348. package/src/telemetry/setup.ts +120 -0
  349. package/src/tools/implementations/agents_discover.ts +121 -0
  350. package/src/tools/implementations/agents_hire.ts +127 -0
  351. package/src/tools/implementations/agents_list.ts +96 -0
  352. package/src/tools/implementations/agents_publish.ts +611 -0
  353. package/src/tools/implementations/agents_read.ts +173 -0
  354. package/src/tools/implementations/agents_write.ts +200 -0
  355. package/src/tools/implementations/ask.ts +411 -0
  356. package/src/tools/implementations/change_model.ts +141 -0
  357. package/src/tools/implementations/conversation_get.ts +661 -0
  358. package/src/tools/implementations/conversation_list.ts +377 -0
  359. package/src/tools/implementations/conversation_search.ts +370 -0
  360. package/src/tools/implementations/delegate.ts +327 -0
  361. package/src/tools/implementations/delegate_crossproject.ts +209 -0
  362. package/src/tools/implementations/delegate_followup.ts +300 -0
  363. package/src/tools/implementations/fs_edit.ts +162 -0
  364. package/src/tools/implementations/fs_glob.ts +182 -0
  365. package/src/tools/implementations/fs_grep.ts +513 -0
  366. package/src/tools/implementations/fs_read.ts +332 -0
  367. package/src/tools/implementations/fs_write.ts +113 -0
  368. package/src/tools/implementations/generate_image.ts +259 -0
  369. package/src/tools/implementations/home_fs.ts +515 -0
  370. package/src/tools/implementations/kill.ts +651 -0
  371. package/src/tools/implementations/learn.ts +166 -0
  372. package/src/tools/implementations/lesson-formatter.ts +38 -0
  373. package/src/tools/implementations/lesson_delete.ts +164 -0
  374. package/src/tools/implementations/lesson_get.ts +105 -0
  375. package/src/tools/implementations/lessons_list.ts +153 -0
  376. package/src/tools/implementations/mcp_resource_read.ts +161 -0
  377. package/src/tools/implementations/mcp_subscribe.ts +158 -0
  378. package/src/tools/implementations/mcp_subscription_stop.ts +85 -0
  379. package/src/tools/implementations/nostr_fetch.ts +149 -0
  380. package/src/tools/implementations/nostr_publish_as_user.ts +353 -0
  381. package/src/tools/implementations/project_list.ts +146 -0
  382. package/src/tools/implementations/rag_add_documents.ts +573 -0
  383. package/src/tools/implementations/rag_create_collection.ts +65 -0
  384. package/src/tools/implementations/rag_delete_collection.ts +68 -0
  385. package/src/tools/implementations/rag_list_collections.ts +77 -0
  386. package/src/tools/implementations/rag_query.ts +107 -0
  387. package/src/tools/implementations/rag_subscription_create.ts +105 -0
  388. package/src/tools/implementations/rag_subscription_delete.ts +80 -0
  389. package/src/tools/implementations/rag_subscription_get.ts +123 -0
  390. package/src/tools/implementations/rag_subscription_list.ts +128 -0
  391. package/src/tools/implementations/report_delete.ts +79 -0
  392. package/src/tools/implementations/report_read.ts +160 -0
  393. package/src/tools/implementations/report_write.ts +278 -0
  394. package/src/tools/implementations/reports_list.ts +77 -0
  395. package/src/tools/implementations/schedule_task.ts +104 -0
  396. package/src/tools/implementations/schedule_task_cancel.ts +62 -0
  397. package/src/tools/implementations/schedule_task_once.ts +128 -0
  398. package/src/tools/implementations/schedule_tasks_list.ts +79 -0
  399. package/src/tools/implementations/search.ts +160 -0
  400. package/src/tools/implementations/shell.ts +553 -0
  401. package/src/tools/implementations/todo.ts +260 -0
  402. package/src/tools/implementations/upload_blob.ts +381 -0
  403. package/src/tools/implementations/web_fetch.ts +153 -0
  404. package/src/tools/implementations/web_search.ts +250 -0
  405. package/src/tools/registry.ts +670 -0
  406. package/src/tools/types.ts +177 -0
  407. package/src/tools/utils.ts +256 -0
  408. package/src/types/event-ids.ts +320 -0
  409. package/src/types/index.ts +46 -0
  410. package/src/utils/agentFetcher.ts +107 -0
  411. package/src/utils/cli-error.ts +29 -0
  412. package/src/utils/conversation-id.ts +27 -0
  413. package/src/utils/conversation-utils.ts +1 -0
  414. package/src/utils/delegation-chain.ts +357 -0
  415. package/src/utils/error-handler.ts +42 -0
  416. package/src/utils/git/gitignore.ts +69 -0
  417. package/src/utils/git/index.ts +2 -0
  418. package/src/utils/git/initializeGitRepo.ts +204 -0
  419. package/src/utils/git/worktree.ts +260 -0
  420. package/src/utils/lessonFormatter.ts +70 -0
  421. package/src/utils/lessonTrust.ts +24 -0
  422. package/src/utils/lockfile.ts +123 -0
  423. package/src/utils/logger.ts +149 -0
  424. package/src/utils/nostr-entity-parser.ts +365 -0
  425. package/src/utils/process.ts +49 -0
  426. package/src/wrapper.ts +262 -0
  427. package/tsconfig.json +41 -0
@@ -0,0 +1,72 @@
1
+ import * as fs from "node:fs";
2
+ import * as path from "node:path";
3
+ import { logger } from "@/utils/logger";
4
+
5
+ /**
6
+ * Simple KV store for agent-specific metadata within a conversation.
7
+ * Each agent in each conversation gets its own isolated metadata store.
8
+ */
9
+ export class AgentMetadataStore {
10
+ private data = new Map<string, unknown>();
11
+ private filePath: string;
12
+
13
+ constructor(
14
+ private conversationId: string,
15
+ private agentSlug: string,
16
+ metadataPath: string
17
+ ) {
18
+ // metadataPath is ~/.tenex/projects/<dTag>/
19
+ const metadataDir = path.join(metadataPath, "metadata");
20
+ this.filePath = path.join(metadataDir, `${conversationId}-${agentSlug}.json`);
21
+ this.load();
22
+ }
23
+
24
+ get<T = unknown>(key: string): T | undefined {
25
+ return this.data.get(key) as T | undefined;
26
+ }
27
+
28
+ set(key: string, value: unknown): void {
29
+ this.data.set(key, value);
30
+ this.save();
31
+ }
32
+
33
+ private load(): void {
34
+ try {
35
+ if (fs.existsSync(this.filePath)) {
36
+ const content = fs.readFileSync(this.filePath, "utf-8");
37
+ const parsed = JSON.parse(content);
38
+ this.data = new Map(Object.entries(parsed));
39
+ logger.debug("[AgentMetadataStore] Loaded metadata", {
40
+ conversationId: this.conversationId.substring(0, 8),
41
+ agentSlug: this.agentSlug,
42
+ keys: Array.from(this.data.keys()),
43
+ });
44
+ }
45
+ } catch (error) {
46
+ logger.error("[AgentMetadataStore] Failed to load metadata", {
47
+ conversationId: this.conversationId.substring(0, 8),
48
+ agentSlug: this.agentSlug,
49
+ error,
50
+ });
51
+ }
52
+ }
53
+
54
+ private save(): void {
55
+ try {
56
+ fs.mkdirSync(path.dirname(this.filePath), { recursive: true });
57
+ const obj = Object.fromEntries(this.data);
58
+ fs.writeFileSync(this.filePath, JSON.stringify(obj, null, 2));
59
+ logger.debug("[AgentMetadataStore] Saved metadata", {
60
+ conversationId: this.conversationId.substring(0, 8),
61
+ agentSlug: this.agentSlug,
62
+ keys: Array.from(this.data.keys()),
63
+ });
64
+ } catch (error) {
65
+ logger.error("[AgentMetadataStore] Failed to save metadata", {
66
+ conversationId: this.conversationId.substring(0, 8),
67
+ agentSlug: this.agentSlug,
68
+ error,
69
+ });
70
+ }
71
+ }
72
+ }
@@ -0,0 +1,59 @@
1
+ import { getProjectContext } from "@/services/projects";
2
+ import { logger } from "@/utils/logger";
3
+
4
+ /**
5
+ * Result of resolving an agent slug
6
+ */
7
+ export interface AgentResolutionResult {
8
+ pubkey: string | null;
9
+ availableSlugs: string[];
10
+ }
11
+
12
+ /**
13
+ * Resolve an agent slug to a pubkey.
14
+ *
15
+ * ONLY accepts agent slugs (e.g., "architect", "claude-code").
16
+ * Does NOT support: pubkeys, npubs, nprofiles, hex prefixes, or agent names.
17
+ *
18
+ * @param slug - Agent slug (case-insensitive)
19
+ * @returns Resolution result with pubkey (or null) and list of available slugs
20
+ */
21
+ export function resolveAgentSlug(slug: string): AgentResolutionResult {
22
+ const trimmedSlug = slug.trim();
23
+ const slugLower = trimmedSlug.toLowerCase();
24
+
25
+ try {
26
+ const projectContext = getProjectContext();
27
+ const agents = projectContext.agentRegistry.getAllAgentsMap();
28
+
29
+ // First, collect all available slugs
30
+ const availableSlugs: string[] = Array.from(agents.keys());
31
+
32
+ // Then look for a match
33
+ for (const [agentSlug, agent] of agents.entries()) {
34
+ if (agentSlug.toLowerCase() === slugLower) {
35
+ return { pubkey: agent.pubkey, availableSlugs };
36
+ }
37
+ }
38
+
39
+ logger.debug("Agent slug not found", { slug: trimmedSlug, availableSlugs });
40
+ return { pubkey: null, availableSlugs };
41
+ } catch (error) {
42
+ logger.debug("Failed to resolve agent slug", { slug: trimmedSlug, error });
43
+ return { pubkey: null, availableSlugs: [] };
44
+ }
45
+ }
46
+
47
+ /**
48
+ * @deprecated Use resolveAgentSlug instead for the full resolution result with available slugs.
49
+ * This wrapper is kept for callers that only need the pubkey without error context.
50
+ *
51
+ * Resolve an agent slug to a pubkey (simplified interface).
52
+ *
53
+ * @param slug - Agent slug (case-insensitive)
54
+ * @returns Pubkey hex string or null if not found
55
+ */
56
+ export function resolveRecipientToPubkey(slug: string): string | null {
57
+ const result = resolveAgentSlug(slug);
58
+ return result.pubkey;
59
+ }
@@ -0,0 +1,281 @@
1
+ /**
2
+ * EscalationService - Handles escalation agent resolution and auto-adding
3
+ *
4
+ * ## Responsibility
5
+ * Resolves escalation targets from config and ensures they're available in the
6
+ * current project context. Handles the auto-add flow when an escalation agent
7
+ * exists in global storage but isn't part of the current project.
8
+ *
9
+ * ## Architecture
10
+ * This service sits between the tool layer (ask.ts) and the agent infrastructure:
11
+ * - Uses AgentStorage for persistence
12
+ * - Uses AgentRegistry for runtime instances
13
+ * - Uses agent-loader utilities for hydration
14
+ * - Coordinates with ProjectContext for daemon notification
15
+ *
16
+ * ## Usage
17
+ * ```typescript
18
+ * import { resolveEscalationTarget } from "@/services/agents/EscalationService";
19
+ *
20
+ * // In a tool implementation
21
+ * const escalationSlug = await resolveEscalationTarget();
22
+ * if (escalationSlug) {
23
+ * // Route through escalation agent
24
+ * }
25
+ * ```
26
+ */
27
+
28
+ import type { AgentRegistry } from "@/agents/AgentRegistry";
29
+ import { agentStorage } from "@/agents/AgentStorage";
30
+ import { createAgentInstance } from "@/agents/agent-loader";
31
+ import { pubkeyFromNsec } from "@/nostr";
32
+ import { resolveRecipientToPubkey } from "@/services/agents/AgentResolution";
33
+ import { config as configService } from "@/services/ConfigService";
34
+ import { getProjectContext } from "@/services/projects";
35
+ import { logger } from "@/utils/logger";
36
+
37
+ export interface EscalationResolutionResult {
38
+ /** The escalation agent's slug */
39
+ slug: string;
40
+ /** Whether the agent was auto-added to the project during this resolution */
41
+ wasAutoAdded: boolean;
42
+ }
43
+
44
+ /**
45
+ * Resolve the escalation agent from config, auto-adding to project if necessary.
46
+ *
47
+ * This function handles the complete escalation target resolution:
48
+ * 1. Reads escalation.agent from config
49
+ * 2. Checks if agent is already in project (fast path)
50
+ * 3. If not, checks global storage and auto-adds to project
51
+ *
52
+ * @returns EscalationResolutionResult if escalation agent is available, null otherwise
53
+ */
54
+ export async function resolveEscalationTarget(): Promise<EscalationResolutionResult | null> {
55
+ try {
56
+ const config = configService.getConfig();
57
+ const escalationAgentSlug = config.escalation?.agent;
58
+
59
+ if (!escalationAgentSlug) {
60
+ return null;
61
+ }
62
+
63
+ // Fast path: check if agent is already in the current project
64
+ const existingPubkey = resolveRecipientToPubkey(escalationAgentSlug);
65
+ if (existingPubkey) {
66
+ return { slug: escalationAgentSlug, wasAutoAdded: false };
67
+ }
68
+
69
+ // Agent not in project - attempt auto-add
70
+ return await autoAddEscalationAgent(escalationAgentSlug);
71
+ } catch (error) {
72
+ // Distinguish between expected errors (config not loaded during startup)
73
+ // and unexpected errors that should be investigated
74
+ const errorMessage = error instanceof Error ? error.message : String(error);
75
+ const isConfigNotLoaded = errorMessage.includes("not loaded") || errorMessage.includes("not initialized");
76
+
77
+ if (isConfigNotLoaded) {
78
+ // Expected during startup - use debug level
79
+ logger.debug("[EscalationService] Config not loaded yet, skipping escalation resolution");
80
+ } else {
81
+ // Unexpected error - use warn level for investigation
82
+ logger.warn("[EscalationService] Unexpected error resolving escalation target", {
83
+ error,
84
+ errorMessage,
85
+ });
86
+ }
87
+ return null;
88
+ }
89
+ }
90
+
91
+ /**
92
+ * Auto-add an escalation agent from global storage to the current project.
93
+ *
94
+ * This is called when the escalation agent is configured but not part of
95
+ * the current project. It performs:
96
+ * 1. Lookup in global storage by slug
97
+ * 2. Association with current project in storage
98
+ * 3. Instance creation and registry registration
99
+ * 4. Daemon notification for routing updates
100
+ *
101
+ * @param escalationAgentSlug - The slug of the escalation agent to add
102
+ * @returns EscalationResolutionResult if successful, null if agent doesn't exist
103
+ */
104
+ async function autoAddEscalationAgent(
105
+ escalationAgentSlug: string
106
+ ): Promise<EscalationResolutionResult | null> {
107
+ // Check global storage for the agent
108
+ const storedAgent = await agentStorage.getAgentBySlug(escalationAgentSlug);
109
+ if (!storedAgent) {
110
+ logger.warn("[EscalationService] Escalation agent configured but not found in system", {
111
+ escalationAgentSlug,
112
+ });
113
+ return null;
114
+ }
115
+
116
+ const projectCtx = getProjectContext();
117
+ const agentRegistry = projectCtx.agentRegistry;
118
+ const projectDTag = agentRegistry.getProjectDTag();
119
+
120
+ if (!projectDTag) {
121
+ logger.warn("[EscalationService] Cannot auto-add escalation agent: no project dTag available");
122
+ return null;
123
+ }
124
+
125
+ logger.info("[EscalationService] Auto-adding escalation agent to project", {
126
+ escalationAgentSlug,
127
+ agentName: storedAgent.name,
128
+ projectDTag,
129
+ });
130
+
131
+ // Get the agent's pubkey from its nsec
132
+ const agentPubkey = pubkeyFromNsec(storedAgent.nsec);
133
+
134
+ // Add agent to project in storage
135
+ await agentStorage.addAgentToProject(agentPubkey, projectDTag);
136
+
137
+ // Reload the agent to get fresh state with the project association
138
+ const freshAgent = await agentStorage.loadAgent(agentPubkey);
139
+ if (!freshAgent) {
140
+ logger.error("[EscalationService] Failed to reload escalation agent after adding to project", {
141
+ escalationAgentSlug,
142
+ agentPubkey: agentPubkey.substring(0, 8),
143
+ });
144
+ return null;
145
+ }
146
+
147
+ // Create agent instance and add to registry
148
+ // Pass projectDTag for project-scoped config resolution
149
+ const agentInstance = createAgentInstance(freshAgent, agentRegistry, projectDTag);
150
+ agentRegistry.addAgent(agentInstance);
151
+
152
+ // Notify the Daemon about the new agent for routing
153
+ projectCtx.notifyAgentAdded(agentInstance);
154
+
155
+ logger.info("[EscalationService] Successfully auto-added escalation agent to project", {
156
+ escalationAgentSlug,
157
+ agentPubkey: agentPubkey.substring(0, 8),
158
+ projectDTag,
159
+ });
160
+
161
+ return { slug: escalationAgentSlug, wasAutoAdded: true };
162
+ }
163
+
164
+ /**
165
+ * Check if an escalation agent is configured (without auto-adding).
166
+ *
167
+ * Use this for quick checks where you don't need to trigger the auto-add flow.
168
+ *
169
+ * @returns The escalation agent slug if configured, null otherwise
170
+ */
171
+ export function getConfiguredEscalationAgent(): string | null {
172
+ try {
173
+ const config = configService.getConfig();
174
+ return config.escalation?.agent || null;
175
+ } catch {
176
+ return null;
177
+ }
178
+ }
179
+
180
+ /**
181
+ * Load escalation agent into a registry proactively during project startup.
182
+ *
183
+ * This function is called during AgentRegistry.loadFromProject() to ensure
184
+ * the escalation agent is available in the "Available Agents" section of
185
+ * all project system prompts.
186
+ *
187
+ * Unlike resolveEscalationTarget() which is reactive (called when ask() is used),
188
+ * this function is proactive and runs during project initialization.
189
+ *
190
+ * @param agentRegistry - The agent registry to load the escalation agent into
191
+ * @param projectDTag - The project's dTag for storage association
192
+ * @returns true if escalation agent was loaded (new or existing), false otherwise
193
+ */
194
+ export async function loadEscalationAgentIntoRegistry(
195
+ agentRegistry: AgentRegistry,
196
+ projectDTag: string | undefined
197
+ ): Promise<boolean> {
198
+ // Validate projectDTag is provided and non-empty (including whitespace-only)
199
+ if (!projectDTag?.trim()) {
200
+ logger.warn("[EscalationService] Cannot load escalation agent: projectDTag is required");
201
+ return false;
202
+ }
203
+
204
+ try {
205
+ const config = configService.getConfig();
206
+ const escalationAgentSlug = config.escalation?.agent;
207
+
208
+ if (!escalationAgentSlug) {
209
+ return false;
210
+ }
211
+
212
+ // Fast path: check if agent is already in registry (avoid duplicate work)
213
+ const existingAgent = agentRegistry.getAgent(escalationAgentSlug);
214
+ if (existingAgent) {
215
+ logger.debug("[EscalationService] Escalation agent already in registry", {
216
+ escalationAgentSlug,
217
+ projectDTag,
218
+ });
219
+ return true;
220
+ }
221
+
222
+ // Check global storage for the agent
223
+ const storedAgent = await agentStorage.getAgentBySlug(escalationAgentSlug);
224
+ if (!storedAgent) {
225
+ logger.warn("[EscalationService] Escalation agent configured but not found in system", {
226
+ escalationAgentSlug,
227
+ });
228
+ return false;
229
+ }
230
+
231
+ logger.info("[EscalationService] Proactively loading escalation agent into registry", {
232
+ escalationAgentSlug,
233
+ agentName: storedAgent.name,
234
+ projectDTag,
235
+ });
236
+
237
+ // Get the agent's pubkey from its nsec
238
+ const agentPubkey = pubkeyFromNsec(storedAgent.nsec);
239
+
240
+ // Add agent to project in storage (idempotent operation)
241
+ await agentStorage.addAgentToProject(agentPubkey, projectDTag);
242
+
243
+ // Reload the agent to get fresh state with the project association
244
+ const freshAgent = await agentStorage.loadAgent(agentPubkey);
245
+ if (!freshAgent) {
246
+ logger.error("[EscalationService] Failed to reload escalation agent after adding to project", {
247
+ escalationAgentSlug,
248
+ agentPubkey: agentPubkey.substring(0, 8),
249
+ });
250
+ return false;
251
+ }
252
+
253
+ // Create agent instance and add to registry
254
+ // Pass projectDTag for project-scoped config resolution
255
+ const agentInstance = createAgentInstance(freshAgent, agentRegistry, projectDTag);
256
+ agentRegistry.addAgent(agentInstance);
257
+
258
+ logger.info("[EscalationService] Successfully loaded escalation agent into registry", {
259
+ escalationAgentSlug,
260
+ agentPubkey: agentPubkey.substring(0, 8),
261
+ projectDTag,
262
+ });
263
+
264
+ return true;
265
+ } catch (error) {
266
+ // Distinguish between expected errors (config not loaded during startup)
267
+ // and unexpected errors that should be investigated
268
+ const errorMessage = error instanceof Error ? error.message : String(error);
269
+ const isConfigNotLoaded = errorMessage.includes("not loaded") || errorMessage.includes("not initialized");
270
+
271
+ if (isConfigNotLoaded) {
272
+ logger.debug("[EscalationService] Config not loaded yet, skipping escalation agent loading");
273
+ } else {
274
+ logger.warn("[EscalationService] Unexpected error loading escalation agent into registry", {
275
+ error,
276
+ errorMessage,
277
+ });
278
+ }
279
+ return false;
280
+ }
281
+ }
@@ -0,0 +1,95 @@
1
+ import { NDKAgentDefinition } from "@/events/NDKAgentDefinition";
2
+ import { collectEvents } from "@/nostr/collectEvents";
3
+ import { logger } from "@/utils/logger";
4
+ import type NDK from "@nostr-dev-kit/ndk";
5
+ import type { NDKFilter } from "@nostr-dev-kit/ndk";
6
+
7
+ /**
8
+ * Options for discovering NDKAgentDefinition events
9
+ */
10
+ export interface AgentDiscoveryOptions {
11
+ /** Text to search for in name/description/role */
12
+ searchText?: string;
13
+ /** Minimum creation timestamp */
14
+ since?: number;
15
+ /** Maximum creation timestamp */
16
+ until?: number;
17
+ }
18
+
19
+ /**
20
+ * Service for discovering NDKAgentDefinition events from the Nostr network
21
+ */
22
+ export class NDKAgentDiscovery {
23
+ constructor(private ndk: NDK) {}
24
+
25
+ /**
26
+ * Discover NDKAgentDefinition events from the network
27
+ */
28
+ async discoverAgents(options: AgentDiscoveryOptions = {}): Promise<NDKAgentDefinition[]> {
29
+ try {
30
+ // Build filter for kind:4199 (NDKAgentDefinition)
31
+ const filter: NDKFilter = {
32
+ kinds: NDKAgentDefinition.kinds,
33
+ };
34
+
35
+ if (options.since) {
36
+ filter.since = options.since;
37
+ }
38
+ if (options.until) {
39
+ filter.until = options.until;
40
+ }
41
+
42
+ logger.debug("Discovering NDKAgentDefinition events", { filter });
43
+
44
+ const events = await collectEvents(this.ndk, filter, {
45
+ subOpts: { groupable: false },
46
+ });
47
+
48
+ const discoveredAgents: NDKAgentDefinition[] = [];
49
+ for (const event of events) {
50
+ try {
51
+ discoveredAgents.push(NDKAgentDefinition.from(event));
52
+ } catch (err) {
53
+ logger.warn("Failed to parse NDKAgentDefinition", { eventId: event.id, err });
54
+ }
55
+ }
56
+
57
+ logger.info(`Found ${discoveredAgents.length} NDKAgentDefinition events`);
58
+
59
+ // Apply local filtering if specified
60
+ let filtered = discoveredAgents;
61
+
62
+ if (options.searchText) {
63
+ filtered = this.filterByText(filtered, options.searchText);
64
+ }
65
+
66
+ // Sort by creation time (newest first)
67
+ filtered.sort((a, b) => (b.created_at || 0) - (a.created_at || 0));
68
+
69
+ return filtered;
70
+ } catch (error) {
71
+ logger.error("Failed to discover NDKAgentDefinition events", { error });
72
+ throw error;
73
+ }
74
+ }
75
+
76
+ /**
77
+ * Filter agents by text search
78
+ */
79
+ private filterByText(agents: NDKAgentDefinition[], searchText: string): NDKAgentDefinition[] {
80
+ const searchLower = searchText.toLowerCase();
81
+
82
+ return agents.filter((agent) => {
83
+ const searchableText = [
84
+ agent.title || "",
85
+ agent.role || "",
86
+ agent.description || "",
87
+ agent.useCriteria || "",
88
+ ]
89
+ .join(" ")
90
+ .toLowerCase();
91
+
92
+ return searchableText.includes(searchLower);
93
+ });
94
+ }
95
+ }
@@ -0,0 +1,7 @@
1
+ export type { AgentDiscoveryOptions } from "./NDKAgentDiscovery";
2
+ export { NDKAgentDiscovery } from "./NDKAgentDiscovery";
3
+ export { resolveAgentSlug, resolveRecipientToPubkey } from "./AgentResolution";
4
+ export type { AgentResolutionResult } from "./AgentResolution";
5
+ export { AgentMetadataStore } from "./AgentMetadataStore";
6
+ export { resolveEscalationTarget, getConfiguredEscalationAgent } from "./EscalationService";
7
+ export type { EscalationResolutionResult } from "./EscalationService";