@agentprojectcontext/apx 1.80.2 → 1.89.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 (838) hide show
  1. package/package.json +9 -8
  2. package/skills/apc-context/SKILL.md +14 -7
  3. package/skills/apx/SKILL.md +62 -2
  4. package/skills/apx-mcp/SKILL.md +42 -15
  5. package/src/core/agent/a2a/peers.js +161 -0
  6. package/src/core/agent/a2a/reply.js +379 -27
  7. package/src/core/agent/abort.js +25 -0
  8. package/src/core/agent/agent-model.js +58 -0
  9. package/src/core/agent/agent-tools.js +101 -0
  10. package/src/core/agent/author-line.js +110 -0
  11. package/src/core/agent/build-agent-system.js +52 -18
  12. package/src/core/agent/channels/voice-context.js +17 -2
  13. package/src/core/agent/closing-floor.js +117 -0
  14. package/src/core/agent/constants.js +119 -11
  15. package/src/core/agent/engine-call.js +56 -0
  16. package/src/core/agent/group/run-group-turn.js +218 -0
  17. package/src/core/agent/group/turn-resolver.js +165 -0
  18. package/src/core/agent/judge.js +138 -11
  19. package/src/core/agent/loop/side-effects.js +106 -3
  20. package/src/core/agent/memory.js +31 -18
  21. package/src/core/agent/model-capabilities.js +47 -0
  22. package/src/core/agent/model-router.js +11 -40
  23. package/src/core/agent/prompt-builder.js +47 -0
  24. package/src/core/agent/prompts/channels/a2a.md +12 -0
  25. package/src/core/agent/prompts/channels/code.md +3 -1
  26. package/src/core/agent/prompts/channels/telegram.md +2 -0
  27. package/src/core/agent/prompts/channels/web_code.md +1 -1
  28. package/src/core/agent/prompts/channels/whatsapp.md +37 -0
  29. package/src/core/agent/prompts/core/agent-base.md +2 -0
  30. package/src/core/agent/prompts/discipline/action.md +1 -0
  31. package/src/core/agent/prompts/discipline/two-segment.md +2 -1
  32. package/src/core/agent/prompts/modes/mobility.md +36 -0
  33. package/src/core/agent/retry.js +42 -0
  34. package/src/core/agent/run-agent.js +322 -25
  35. package/src/core/agent/run-turn.js +253 -0
  36. package/src/core/agent/self-memory.js +18 -52
  37. package/src/core/agent/skills/agent-skills.js +118 -0
  38. package/src/core/agent/skills/catalog.js +1 -1
  39. package/src/core/agent/skills/declared.js +13 -0
  40. package/src/core/agent/skills/index-store.js +8 -1
  41. package/src/core/agent/skills/inspector.js +20 -3
  42. package/src/core/agent/skills/loader.js +18 -3
  43. package/src/core/agent/skills/media.js +121 -0
  44. package/src/core/agent/skills/origin.js +61 -0
  45. package/src/core/agent/skills/sections.js +136 -0
  46. package/src/core/agent/super-agent.js +54 -14
  47. package/src/core/agent/tools/handlers/_calendar.js +50 -0
  48. package/src/core/agent/tools/handlers/add-mcp.js +103 -0
  49. package/src/core/agent/tools/handlers/asana-create-task.js +3 -1
  50. package/src/core/agent/tools/handlers/attach-media.js +56 -0
  51. package/src/core/agent/tools/handlers/calendar-create-event.js +38 -0
  52. package/src/core/agent/tools/handlers/calendar-find-slot.js +39 -0
  53. package/src/core/agent/tools/handlers/calendar-list-events.js +39 -0
  54. package/src/core/agent/tools/handlers/calendar-update-event.js +35 -0
  55. package/src/core/agent/tools/handlers/call-agent.js +14 -6
  56. package/src/core/agent/tools/handlers/call-runtime.js +27 -49
  57. package/src/core/agent/tools/handlers/comment-task.js +78 -0
  58. package/src/core/agent/tools/handlers/complete-task.js +60 -0
  59. package/src/core/agent/tools/handlers/configure-agent.js +70 -0
  60. package/src/core/agent/tools/handlers/create-agent.js +68 -0
  61. package/src/core/agent/tools/handlers/create-task.js +41 -3
  62. package/src/core/agent/tools/handlers/import-agent.js +5 -5
  63. package/src/core/agent/tools/handlers/list-mcp-tools.js +83 -0
  64. package/src/core/agent/tools/handlers/list-routines.js +46 -0
  65. package/src/core/agent/tools/handlers/list-tasks.js +8 -1
  66. package/src/core/agent/tools/handlers/mark-commitment.js +57 -0
  67. package/src/core/agent/tools/handlers/read-skill.js +64 -0
  68. package/src/core/agent/tools/handlers/remember-routine.js +2 -8
  69. package/src/core/agent/tools/handlers/remember.js +82 -6
  70. package/src/core/agent/tools/handlers/remove-agent.js +42 -0
  71. package/src/core/agent/tools/handlers/run-routine.js +94 -0
  72. package/src/core/agent/tools/handlers/run-shell.js +44 -2
  73. package/src/core/agent/tools/handlers/send-telegram.js +41 -19
  74. package/src/core/agent/tools/handlers/set-agent-prompt.js +44 -0
  75. package/src/core/agent/tools/handlers/view-media.js +69 -0
  76. package/src/core/agent/tools/handlers/write-agent-memory.js +52 -0
  77. package/src/core/agent/tools/helpers.js +36 -4
  78. package/src/core/agent/tools/names.js +64 -0
  79. package/src/core/agent/tools/registry-bridge.js +24 -1
  80. package/src/core/agent/tools/registry.js +79 -0
  81. package/src/core/agent/tools/tool-call-parser.js +136 -13
  82. package/src/core/agent/vision-bridge.js +69 -0
  83. package/src/core/apc/agent-identity.js +74 -0
  84. package/src/core/apc/agent-rename-refs.js +187 -0
  85. package/src/core/apc/agent-write.js +312 -0
  86. package/src/core/apc/agents-vault.js +1 -1
  87. package/src/core/apc/blob-keys.js +42 -0
  88. package/src/core/apc/frontmatter.js +166 -10
  89. package/src/core/apc/parser.js +33 -83
  90. package/src/core/apc/paths.js +4 -6
  91. package/src/core/apc/project-memory.js +44 -0
  92. package/src/core/apc/projects-helpers.js +33 -0
  93. package/src/core/apc/scaffold.js +36 -16
  94. package/src/core/channels/telegram/ask-callbacks.js +103 -0
  95. package/src/core/channels/telegram/dispatch.js +154 -30
  96. package/src/core/channels/telegram/helpers.js +59 -7
  97. package/src/core/channels/telegram/inbound/audio.js +26 -30
  98. package/src/core/channels/telegram/inbound/file.js +22 -32
  99. package/src/core/channels/telegram/inbound/photo.js +24 -28
  100. package/src/core/channels/telegram/progress-gate.js +76 -0
  101. package/src/core/channels/telegram/reply.js +151 -43
  102. package/src/core/channels/telegram/voice-note.js +150 -0
  103. package/src/core/config/index.js +53 -54
  104. package/src/core/config/paths.js +117 -31
  105. package/src/core/config/redact.js +89 -4
  106. package/src/core/config/secret-values.js +2 -4
  107. package/src/core/constants/actors.js +5 -0
  108. package/src/core/constants/channels.js +3 -1
  109. package/src/core/constants/task-categories.js +73 -0
  110. package/src/core/constants/task-fields.js +28 -0
  111. package/src/core/engines/_globs.js +33 -0
  112. package/src/core/engines/anthropic.js +19 -1
  113. package/src/core/engines/catalog.js +20 -0
  114. package/src/core/engines/gemini.js +84 -16
  115. package/src/core/engines/index.js +19 -3
  116. package/src/core/engines/mock.js +145 -1
  117. package/src/core/engines/openai-compatible.js +150 -15
  118. package/src/core/engines/presets.js +36 -9
  119. package/src/core/engines/zen.js +131 -0
  120. package/src/core/events/bus.js +140 -0
  121. package/src/core/events/mascot-notify.js +156 -0
  122. package/src/core/http-tools/browser.js +366 -36
  123. package/src/core/http-tools/catalog.js +206 -22
  124. package/src/core/http-tools/grep.js +62 -7
  125. package/src/core/http-tools/registry.js +3 -1
  126. package/src/core/i18n/en.js +34 -3
  127. package/src/core/i18n/es.js +36 -4
  128. package/src/core/i18n/index.js +5 -5
  129. package/src/core/i18n/pt.js +32 -3
  130. package/src/core/identity/self.js +14 -1
  131. package/src/core/images/engines/a1111.js +219 -0
  132. package/src/core/images/engines/index.js +187 -0
  133. package/src/core/images/engines/mock.js +74 -0
  134. package/src/core/images/engines/openai.js +130 -0
  135. package/src/core/images/engines/sdcpp.js +204 -0
  136. package/src/core/images/engines/shared.js +218 -0
  137. package/src/core/images/generate.js +260 -0
  138. package/src/core/integrations/catalog.js +8 -3
  139. package/src/core/integrations/plugins/_google-oauth.js +179 -0
  140. package/src/core/integrations/plugins/asana.js +7 -3
  141. package/src/core/integrations/plugins/calendar.js +404 -0
  142. package/src/core/integrations/store.js +2 -0
  143. package/src/core/memory/broker.js +16 -1
  144. package/src/core/memory/compactor.js +19 -3
  145. package/src/core/memory/consolidate.js +2 -2
  146. package/src/core/memory/dated-log.js +66 -0
  147. package/src/core/memory/embed-engines/custom.js +59 -0
  148. package/src/core/memory/embed-engines/gemini.js +9 -3
  149. package/src/core/memory/embed-engines/index.js +87 -15
  150. package/src/core/memory/embeddings.js +52 -24
  151. package/src/core/memory/index.js +13 -3
  152. package/src/core/memory/indexer.js +83 -27
  153. package/src/core/memory/prune.js +182 -0
  154. package/src/core/memory/store.js +22 -0
  155. package/src/core/memory/summarizer.js +72 -8
  156. package/src/core/mobility/answer.js +80 -0
  157. package/src/core/mobility/geofence.js +667 -0
  158. package/src/core/mobility/osm-route.js +282 -0
  159. package/src/core/mobility/preferences.js +91 -0
  160. package/src/core/mobility/state.js +245 -0
  161. package/src/core/mobility/trip-event.js +384 -0
  162. package/src/core/net/tailscale.js +168 -0
  163. package/src/core/profiles/bundled/secretary/PROFILE.md +32 -42
  164. package/src/core/profiles/bundled/secretary/config.schema.es.json +68 -0
  165. package/src/core/profiles/bundled/secretary/config.schema.json +30 -2
  166. package/src/core/profiles/bundled/secretary/profile.json +3 -1
  167. package/src/core/profiles/bundled/secretary/routines/a2a-sweep.json +20 -0
  168. package/src/core/profiles/bundled/secretary/routines/day-close.json +4 -1
  169. package/src/core/profiles/bundled/secretary/routines/day-open.json +7 -1
  170. package/src/core/profiles/bundled/secretary/routines/watch.json +13 -2
  171. package/src/core/profiles/lifecycle.js +243 -19
  172. package/src/core/profiles/paths.js +12 -0
  173. package/src/core/profiles/store.js +47 -0
  174. package/src/core/routines/active-runs.js +213 -0
  175. package/src/core/routines/delivery.js +612 -0
  176. package/src/core/routines/header.js +88 -0
  177. package/src/core/routines/index.js +26 -0
  178. package/src/core/routines/run-log.js +78 -0
  179. package/src/core/routines/runner.js +629 -66
  180. package/src/core/routines/signals.js +75 -0
  181. package/src/core/runtime-skills/apc-context/SKILL.md +14 -7
  182. package/src/core/runtime-skills/apx/SKILL.md +93 -1
  183. package/src/core/runtime-skills/apx-agency-agents/SKILL.md +2 -2
  184. package/src/core/runtime-skills/apx-agent/SKILL.md +134 -19
  185. package/src/core/runtime-skills/apx-commitment/SKILL.md +134 -0
  186. package/src/core/runtime-skills/apx-image/SKILL.md +60 -0
  187. package/src/core/runtime-skills/apx-integrations/SKILL.md +82 -0
  188. package/src/core/runtime-skills/apx-mcp/SKILL.md +45 -14
  189. package/src/core/runtime-skills/apx-mcp-builder/SKILL.md +4 -4
  190. package/src/core/runtime-skills/apx-profile/SKILL.md +27 -2
  191. package/src/core/runtime-skills/apx-project/SKILL.md +23 -2
  192. package/src/core/runtime-skills/apx-routine/SKILL.md +40 -17
  193. package/src/core/runtime-skills/apx-runtime/SKILL.md +124 -14
  194. package/src/core/runtime-skills/apx-sessions/SKILL.md +7 -6
  195. package/src/core/runtime-skills/apx-skill-builder/SKILL.md +15 -13
  196. package/src/core/runtime-skills/apx-task/SKILL.md +79 -26
  197. package/src/core/runtime-skills/apx-telegram/SKILL.md +12 -12
  198. package/src/core/runtime-skills/apx-transcribe/SKILL.md +56 -0
  199. package/src/core/runtime-skills/apx-voice/SKILL.md +27 -8
  200. package/src/core/runtime-skills/claude-code/SKILL.md +8 -0
  201. package/src/core/runtime-skills/openrouter/SKILL.md +8 -2
  202. package/src/core/runtimes/_spawn.js +9 -1
  203. package/src/core/runtimes/claude-code.js +11 -2
  204. package/src/core/runtimes/codex.js +44 -10
  205. package/src/core/runtimes/index.js +17 -2
  206. package/src/core/runtimes/opencode.js +88 -9
  207. package/src/core/runtimes/outcome.js +119 -0
  208. package/src/core/sessions/index.js +193 -1
  209. package/src/core/stores/agent-inbox.js +109 -23
  210. package/src/core/stores/code-sessions.js +21 -0
  211. package/src/core/stores/commitments.js +27 -3
  212. package/src/core/stores/conversations.js +220 -20
  213. package/src/core/stores/deliveries.js +177 -0
  214. package/src/core/stores/media-archive.js +228 -0
  215. package/src/core/stores/messages.js +1096 -112
  216. package/src/core/stores/organization.js +34 -0
  217. package/src/core/stores/project-memory.js +71 -0
  218. package/src/core/stores/routine-memory.js +16 -8
  219. package/src/core/stores/routines.js +27 -49
  220. package/src/core/stores/sessions.js +4 -8
  221. package/src/core/stores/tasks.js +212 -18
  222. package/src/core/stores/turn-record.js +209 -0
  223. package/src/core/tasks/columns.js +136 -0
  224. package/src/core/tasks/comment-turn.js +258 -0
  225. package/src/core/util/time.js +13 -0
  226. package/src/core/voice/engines/index.js +54 -1
  227. package/src/core/voice/engines/openai.js +50 -4
  228. package/src/core/voice/opus.js +67 -0
  229. package/src/core/voice/pronounceable.js +43 -0
  230. package/src/core/voice/transcription.js +4 -0
  231. package/src/core/voice/tts.js +114 -24
  232. package/src/host/daemon/active-turns.js +188 -0
  233. package/src/host/daemon/api/admin-config.js +9 -0
  234. package/src/host/daemon/api/agents.js +99 -90
  235. package/src/host/daemon/api/artifact-preview.js +7 -6
  236. package/src/host/daemon/api/artifacts.js +3 -2
  237. package/src/host/daemon/api/code.js +55 -9
  238. package/src/host/daemon/api/commitments.js +11 -0
  239. package/src/host/daemon/api/confirm.js +3 -2
  240. package/src/host/daemon/api/conversations.js +543 -35
  241. package/src/host/daemon/api/deck.js +9 -8
  242. package/src/host/daemon/api/deliveries.js +33 -0
  243. package/src/host/daemon/api/desktop.js +5 -4
  244. package/src/host/daemon/api/embeddings.js +15 -6
  245. package/src/host/daemon/api/engines.js +59 -8
  246. package/src/host/daemon/api/exec.js +437 -121
  247. package/src/host/daemon/api/groups.js +215 -0
  248. package/src/host/daemon/api/images.js +107 -0
  249. package/src/host/daemon/api/inbox.js +123 -2
  250. package/src/host/daemon/api/integrations.js +64 -2
  251. package/src/host/daemon/api/mcps.js +7 -6
  252. package/src/host/daemon/api/media.js +283 -0
  253. package/src/host/daemon/api/mobility.js +177 -0
  254. package/src/host/daemon/api/net.js +182 -0
  255. package/src/host/daemon/api/pairing.js +38 -5
  256. package/src/host/daemon/api/profiles.js +30 -2
  257. package/src/host/daemon/api/routines.js +36 -4
  258. package/src/host/daemon/api/runtimes.js +74 -39
  259. package/src/host/daemon/api/sessions-search.js +7 -2
  260. package/src/host/daemon/api/sessions.js +44 -2
  261. package/src/host/daemon/api/shared.js +127 -20
  262. package/src/host/daemon/api/skills.js +11 -4
  263. package/src/host/daemon/api/super-agent.js +384 -53
  264. package/src/host/daemon/api/tasks.js +180 -10
  265. package/src/host/daemon/api/telegram.js +11 -10
  266. package/src/host/daemon/api/thread-faces.js +159 -0
  267. package/src/host/daemon/api/top-level.js +3 -3
  268. package/src/host/daemon/api/transcribe.js +11 -10
  269. package/src/host/daemon/api/tts.js +97 -4
  270. package/src/host/daemon/api/turn-abort.js +23 -0
  271. package/src/host/daemon/api/turns.js +49 -0
  272. package/src/host/daemon/api/voice.js +5 -4
  273. package/src/host/daemon/api/web.js +98 -0
  274. package/src/host/daemon/api.js +39 -0
  275. package/src/host/daemon/delivery-sweep.js +58 -0
  276. package/src/host/daemon/desktop-ws.js +5 -23
  277. package/src/host/daemon/events-ws.js +273 -0
  278. package/src/host/daemon/index.js +59 -15
  279. package/src/host/daemon/plugins/desktop/index.js +17 -4
  280. package/src/host/daemon/plugins/telegram/index.js +78 -40
  281. package/src/host/daemon/pty-bridge.py +99 -0
  282. package/src/host/daemon/routines-scheduler.js +1 -0
  283. package/src/host/daemon/smoke.js +1 -2
  284. package/src/host/daemon/terminal-ws.js +132 -0
  285. package/src/host/daemon/tts-keepwarm.js +87 -0
  286. package/src/host/daemon/wakeup.js +11 -6
  287. package/src/host/daemon/whisper-server.js +44 -0
  288. package/src/host/daemon/whisper-server.py +70 -13
  289. package/src/host/daemon/ws-auth.js +28 -0
  290. package/src/interfaces/android/app/build.gradle +42 -0
  291. package/src/interfaces/android/app/proguard-rules.pro +4 -0
  292. package/src/interfaces/android/app/src/main/AndroidManifest.xml +139 -0
  293. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/AlertScreen.java +139 -0
  294. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/AndroidAutoDetector.java +106 -0
  295. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/ApxCarAppService.java +57 -0
  296. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/ApxPreferences.java +165 -0
  297. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/CarAlertStore.java +84 -0
  298. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/CarMessageActionReceiver.java +47 -0
  299. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/CarMessageNotification.java +152 -0
  300. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/DaemonAddress.java +35 -0
  301. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/DaemonClient.java +339 -0
  302. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/DeviceLocation.java +38 -0
  303. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/ErrandScreen.java +127 -0
  304. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/MainActivity.java +872 -0
  305. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/MapsNavigationDetector.java +63 -0
  306. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/MapsNavigationListenerService.java +453 -0
  307. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/MapsShareIntentParser.java +93 -0
  308. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/MascotBlobCatalog.java +66 -0
  309. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/MascotOverlayService.java +448 -0
  310. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/MascotView.java +249 -0
  311. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/MessageFrameParser.java +240 -0
  312. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/NotifyChannels.java +69 -0
  313. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/ProximityActionReceiver.java +78 -0
  314. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/ProximityNotification.java +161 -0
  315. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/StartupReceiver.java +57 -0
  316. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/TravelEventGate.java +62 -0
  317. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/TravelStatusBanner.java +116 -0
  318. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/TripLocationService.java +272 -0
  319. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/TripPlacesSheet.java +203 -0
  320. package/src/interfaces/android/app/src/main/java/dev/agentprojectcontext/apx/TripScreen.java +182 -0
  321. package/src/interfaces/android/app/src/main/res/drawable/app_background.xml +12 -0
  322. package/src/interfaces/android/app/src/main/res/drawable/ic_apx_app.xml +10 -0
  323. package/src/interfaces/android/app/src/main/res/drawable/ic_apx_launcher_foreground.xml +12 -0
  324. package/src/interfaces/android/app/src/main/res/drawable/ic_apx_notification.xml +22 -0
  325. package/src/interfaces/android/app/src/main/res/drawable/ic_trip_car.xml +37 -0
  326. package/src/interfaces/android/app/src/main/res/drawable-nodpi/apx_logo.png +0 -0
  327. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_amatista.png +0 -0
  328. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_aqua.png +0 -0
  329. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_brasa.png +0 -0
  330. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_campana.png +0 -0
  331. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_caracol.png +0 -0
  332. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_carbon.png +0 -0
  333. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_cobalto.png +0 -0
  334. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_cometa.png +0 -0
  335. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_coral.png +0 -0
  336. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_cubi.png +0 -0
  337. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_eclipse.png +0 -0
  338. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_faro.png +0 -0
  339. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_gajo.png +0 -0
  340. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_iris.png +0 -0
  341. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_kiwi.png +0 -0
  342. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_laguna.png +0 -0
  343. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_lila.png +0 -0
  344. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_menta.png +0 -0
  345. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_nimbo.png +0 -0
  346. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_noche.png +0 -0
  347. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_onyx.png +0 -0
  348. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_orbita.png +0 -0
  349. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_ovni.png +0 -0
  350. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_papa.png +0 -0
  351. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_parche.png +0 -0
  352. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_peon.png +0 -0
  353. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_perla.png +0 -0
  354. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_pino.png +0 -0
  355. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_quad.png +0 -0
  356. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_rubi.png +0 -0
  357. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_saturno.png +0 -0
  358. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_trebol.png +0 -0
  359. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_trino.png +0 -0
  360. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_volcan.png +0 -0
  361. package/src/interfaces/android/app/src/main/res/drawable-nodpi/mascot_zafiro.png +0 -0
  362. package/src/interfaces/android/app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml +5 -0
  363. package/src/interfaces/android/app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml +5 -0
  364. package/src/interfaces/android/app/src/main/res/raw/apx_notification.mp3 +0 -0
  365. package/src/interfaces/android/app/src/main/res/values/colors.xml +4 -0
  366. package/src/interfaces/android/app/src/main/res/values/strings.xml +25 -0
  367. package/src/interfaces/android/app/src/main/res/values/styles.xml +10 -0
  368. package/src/interfaces/android/app/src/main/res/values-v31/styles.xml +14 -0
  369. package/src/interfaces/android/app/src/main/res/xml/automotive_app_desc.xml +9 -0
  370. package/src/interfaces/android/app/src/main/res/xml/network_security_config.xml +10 -0
  371. package/src/interfaces/android/app/src/test/java/dev/agentprojectcontext/apx/AndroidAutoDetectorTest.java +85 -0
  372. package/src/interfaces/android/app/src/test/java/dev/agentprojectcontext/apx/CarAlertStoreTest.java +104 -0
  373. package/src/interfaces/android/app/src/test/java/dev/agentprojectcontext/apx/DaemonAddressTest.java +23 -0
  374. package/src/interfaces/android/app/src/test/java/dev/agentprojectcontext/apx/MapsNavigationDetectorTest.java +69 -0
  375. package/src/interfaces/android/app/src/test/java/dev/agentprojectcontext/apx/MapsShareIntentParserTest.java +31 -0
  376. package/src/interfaces/android/app/src/test/java/dev/agentprojectcontext/apx/MessageFrameParserTest.java +180 -0
  377. package/src/interfaces/android/app/src/test/java/dev/agentprojectcontext/apx/TravelEventGateTest.java +64 -0
  378. package/src/interfaces/android/app/src/test/java/dev/agentprojectcontext/apx/TripPlacesSheetTest.java +66 -0
  379. package/src/interfaces/android/build.gradle +3 -0
  380. package/src/interfaces/android/gradle/wrapper/gradle-wrapper.jar +0 -0
  381. package/src/interfaces/android/gradle/wrapper/gradle-wrapper.properties +9 -0
  382. package/src/interfaces/android/gradle.properties +3 -0
  383. package/src/interfaces/android/gradlew +248 -0
  384. package/src/interfaces/android/gradlew.bat +82 -0
  385. package/src/interfaces/android/settings.gradle +18 -0
  386. package/src/interfaces/cli/commands/a2a.js +145 -4
  387. package/src/interfaces/cli/commands/agent.js +247 -22
  388. package/src/interfaces/cli/commands/code.js +1 -1
  389. package/src/interfaces/cli/commands/commitment.js +5 -0
  390. package/src/interfaces/cli/commands/config.js +85 -6
  391. package/src/interfaces/cli/commands/exec.js +90 -1
  392. package/src/interfaces/cli/commands/image.js +314 -0
  393. package/src/interfaces/cli/commands/mcp.js +87 -23
  394. package/src/interfaces/cli/commands/memory.js +35 -22
  395. package/src/interfaces/cli/commands/panel.js +94 -0
  396. package/src/interfaces/cli/commands/profile.js +14 -0
  397. package/src/interfaces/cli/commands/project.js +29 -0
  398. package/src/interfaces/cli/commands/routine.js +45 -10
  399. package/src/interfaces/cli/commands/runtime.js +30 -7
  400. package/src/interfaces/cli/commands/session.js +90 -38
  401. package/src/interfaces/cli/commands/sessions.js +35 -2
  402. package/src/interfaces/cli/commands/skills.js +15 -9
  403. package/src/interfaces/cli/commands/status.js +2 -3
  404. package/src/interfaces/cli/commands/task.js +54 -5
  405. package/src/interfaces/cli/commands/telegram.js +12 -4
  406. package/src/interfaces/cli/commands/transcribe.js +177 -0
  407. package/src/interfaces/cli/help/index.js +311 -72
  408. package/src/interfaces/cli/http.js +61 -13
  409. package/src/interfaces/cli/index.js +1 -1
  410. package/src/interfaces/cli/routes/agent.js +5 -4
  411. package/src/interfaces/cli/routes/commitment.js +3 -2
  412. package/src/interfaces/cli/routes/config.js +7 -2
  413. package/src/interfaces/cli/routes/image.js +11 -0
  414. package/src/interfaces/cli/routes/index.js +2 -0
  415. package/src/interfaces/cli/routes/log.js +1 -1
  416. package/src/interfaces/cli/routes/memory.js +3 -2
  417. package/src/interfaces/cli/routes/panel.js +15 -2
  418. package/src/interfaces/cli/routes/profile.js +3 -2
  419. package/src/interfaces/cli/routes/transcribe.js +10 -0
  420. package/src/interfaces/cli/stdin.js +29 -0
  421. package/src/interfaces/desktop/assets/blobs/amatista.png +0 -0
  422. package/src/interfaces/desktop/assets/blobs/aqua.png +0 -0
  423. package/src/interfaces/desktop/assets/blobs/brasa.png +0 -0
  424. package/src/interfaces/desktop/assets/blobs/campana.png +0 -0
  425. package/src/interfaces/desktop/assets/blobs/caracol.png +0 -0
  426. package/src/interfaces/desktop/assets/blobs/carbon.png +0 -0
  427. package/src/interfaces/desktop/assets/blobs/cobalto.png +0 -0
  428. package/src/interfaces/desktop/assets/blobs/cometa.png +0 -0
  429. package/src/interfaces/desktop/assets/blobs/coral.png +0 -0
  430. package/src/interfaces/desktop/assets/blobs/cubi.png +0 -0
  431. package/src/interfaces/desktop/assets/blobs/eclipse.png +0 -0
  432. package/src/interfaces/desktop/assets/blobs/faro.png +0 -0
  433. package/src/interfaces/desktop/assets/blobs/gajo.png +0 -0
  434. package/src/interfaces/desktop/assets/blobs/iris.png +0 -0
  435. package/src/interfaces/desktop/assets/blobs/kiwi.png +0 -0
  436. package/src/interfaces/desktop/assets/blobs/laguna.png +0 -0
  437. package/src/interfaces/desktop/assets/blobs/lila.png +0 -0
  438. package/src/interfaces/desktop/assets/blobs/menta.png +0 -0
  439. package/src/interfaces/desktop/assets/blobs/nimbo.png +0 -0
  440. package/src/interfaces/desktop/assets/blobs/noche.png +0 -0
  441. package/src/interfaces/desktop/assets/blobs/onyx.png +0 -0
  442. package/src/interfaces/desktop/assets/blobs/orbita.png +0 -0
  443. package/src/interfaces/desktop/assets/blobs/ovni.png +0 -0
  444. package/src/interfaces/desktop/assets/blobs/papa.png +0 -0
  445. package/src/interfaces/desktop/assets/blobs/parche.png +0 -0
  446. package/src/interfaces/desktop/assets/blobs/peon.png +0 -0
  447. package/src/interfaces/desktop/assets/blobs/perla.png +0 -0
  448. package/src/interfaces/desktop/assets/blobs/pino.png +0 -0
  449. package/src/interfaces/desktop/assets/blobs/quad.png +0 -0
  450. package/src/interfaces/desktop/assets/blobs/rubi.png +0 -0
  451. package/src/interfaces/desktop/assets/blobs/saturno.png +0 -0
  452. package/src/interfaces/desktop/assets/blobs/trebol.png +0 -0
  453. package/src/interfaces/desktop/assets/blobs/trino.png +0 -0
  454. package/src/interfaces/desktop/assets/blobs/volcan.png +0 -0
  455. package/src/interfaces/desktop/assets/blobs/zafiro.png +0 -0
  456. package/src/interfaces/desktop/assets/notification.mp3 +0 -0
  457. package/src/interfaces/desktop/main.js +473 -29
  458. package/src/interfaces/desktop/mascot-blobs.js +41 -0
  459. package/src/interfaces/desktop/mascot-preload.js +32 -0
  460. package/src/interfaces/desktop/mascot.css +186 -0
  461. package/src/interfaces/desktop/mascot.html +40 -0
  462. package/src/interfaces/desktop/mascot.js +163 -0
  463. package/src/interfaces/desktop/preload.js +10 -0
  464. package/src/interfaces/desktop/renderer.js +308 -48
  465. package/src/interfaces/desktop/style.css +34 -0
  466. package/src/interfaces/mcp-server/index.js +87 -0
  467. package/src/interfaces/tui/_shims/util-locale.ts +0 -2
  468. package/src/interfaces/tui/app.tsx +0 -6
  469. package/src/interfaces/tui/attach.ts +0 -1
  470. package/src/interfaces/tui/context/sdk-apx.tsx +0 -4
  471. package/src/interfaces/tui/plugin/api.tsx +0 -3
  472. package/src/interfaces/tui/plugin/runtime.ts +0 -3
  473. package/src/interfaces/tui/thread.ts +0 -16
  474. package/src/interfaces/web/README.md +22 -14
  475. package/src/interfaces/web/dist/assets/claude-XtpLmGtF.webp +0 -0
  476. package/src/interfaces/web/dist/assets/codex-DExPUgvh.webp +0 -0
  477. package/src/interfaces/web/dist/assets/index-BEoRgIqd.css +32 -0
  478. package/src/interfaces/web/dist/assets/index-BEoRgIqd.css.br +0 -0
  479. package/src/interfaces/web/dist/assets/index-BEoRgIqd.css.gz +0 -0
  480. package/src/interfaces/web/dist/assets/index-C6fXHc1p.js +1074 -0
  481. package/src/interfaces/web/dist/assets/index-C6fXHc1p.js.br +0 -0
  482. package/src/interfaces/web/dist/assets/index-C6fXHc1p.js.gz +0 -0
  483. package/src/interfaces/web/dist/assets/index-C6fXHc1p.js.map +1 -0
  484. package/src/interfaces/web/dist/assets/index-C6fXHc1p.js.map.br +0 -0
  485. package/src/interfaces/web/dist/assets/index-C6fXHc1p.js.map.gz +0 -0
  486. package/src/interfaces/web/dist/favicon/dark/site.webmanifest +12 -6
  487. package/src/interfaces/web/dist/favicon/white/site.webmanifest +12 -6
  488. package/src/interfaces/web/dist/index.html +22 -6
  489. package/src/interfaces/web/dist/index.html.br +0 -0
  490. package/src/interfaces/web/dist/index.html.gz +0 -0
  491. package/src/interfaces/web/dist/manifest.webmanifest +25 -0
  492. package/src/interfaces/web/dist/modules/blobs/amatista.png +0 -0
  493. package/src/interfaces/web/dist/modules/blobs/aqua.png +0 -0
  494. package/src/interfaces/web/dist/modules/blobs/brasa.png +0 -0
  495. package/src/interfaces/web/dist/modules/blobs/campana.png +0 -0
  496. package/src/interfaces/web/dist/modules/blobs/caracol.png +0 -0
  497. package/src/interfaces/web/dist/modules/blobs/carbon.png +0 -0
  498. package/src/interfaces/web/dist/modules/blobs/cobalto.png +0 -0
  499. package/src/interfaces/web/dist/modules/blobs/cometa.png +0 -0
  500. package/src/interfaces/web/dist/modules/blobs/coral.png +0 -0
  501. package/src/interfaces/web/dist/modules/blobs/cubi.png +0 -0
  502. package/src/interfaces/web/dist/modules/blobs/eclipse.png +0 -0
  503. package/src/interfaces/web/dist/modules/blobs/faro.png +0 -0
  504. package/src/interfaces/web/dist/modules/blobs/gajo.png +0 -0
  505. package/src/interfaces/web/dist/modules/blobs/iris.png +0 -0
  506. package/src/interfaces/web/dist/modules/blobs/kiwi.png +0 -0
  507. package/src/interfaces/web/dist/modules/blobs/laguna.png +0 -0
  508. package/src/interfaces/web/dist/modules/blobs/lila.png +0 -0
  509. package/src/interfaces/web/dist/modules/blobs/menta.png +0 -0
  510. package/src/interfaces/web/dist/modules/blobs/nimbo.png +0 -0
  511. package/src/interfaces/web/dist/modules/blobs/noche.png +0 -0
  512. package/src/interfaces/web/dist/modules/blobs/onyx.png +0 -0
  513. package/src/interfaces/web/dist/modules/blobs/orbita.png +0 -0
  514. package/src/interfaces/web/dist/modules/blobs/ovni.png +0 -0
  515. package/src/interfaces/web/dist/modules/blobs/papa.png +0 -0
  516. package/src/interfaces/web/dist/modules/blobs/parche.png +0 -0
  517. package/src/interfaces/web/dist/modules/blobs/peon.png +0 -0
  518. package/src/interfaces/web/dist/modules/blobs/perla.png +0 -0
  519. package/src/interfaces/web/dist/modules/blobs/pino.png +0 -0
  520. package/src/interfaces/web/dist/modules/blobs/quad.png +0 -0
  521. package/src/interfaces/web/dist/modules/blobs/rubi.png +0 -0
  522. package/src/interfaces/web/dist/modules/blobs/saturno.png +0 -0
  523. package/src/interfaces/web/dist/modules/blobs/trebol.png +0 -0
  524. package/src/interfaces/web/dist/modules/blobs/trino.png +0 -0
  525. package/src/interfaces/web/dist/modules/blobs/volcan.png +0 -0
  526. package/src/interfaces/web/dist/modules/blobs/zafiro.png +0 -0
  527. package/src/interfaces/web/dist/sw.js +106 -0
  528. package/src/interfaces/web/dist/sw.js.br +0 -0
  529. package/src/interfaces/web/dist/sw.js.gz +0 -0
  530. package/src/interfaces/web/eslint.config.js +83 -0
  531. package/src/interfaces/web/index.html +20 -4
  532. package/src/interfaces/web/package-lock.json +1651 -1280
  533. package/src/interfaces/web/package.json +9 -10
  534. package/src/interfaces/web/pnpm-lock.yaml +867 -869
  535. package/src/interfaces/web/public/favicon/dark/site.webmanifest +12 -6
  536. package/src/interfaces/web/public/favicon/white/site.webmanifest +12 -6
  537. package/src/interfaces/web/public/manifest.webmanifest +25 -0
  538. package/src/interfaces/web/public/modules/blobs/amatista.png +0 -0
  539. package/src/interfaces/web/public/modules/blobs/aqua.png +0 -0
  540. package/src/interfaces/web/public/modules/blobs/brasa.png +0 -0
  541. package/src/interfaces/web/public/modules/blobs/campana.png +0 -0
  542. package/src/interfaces/web/public/modules/blobs/caracol.png +0 -0
  543. package/src/interfaces/web/public/modules/blobs/carbon.png +0 -0
  544. package/src/interfaces/web/public/modules/blobs/cobalto.png +0 -0
  545. package/src/interfaces/web/public/modules/blobs/cometa.png +0 -0
  546. package/src/interfaces/web/public/modules/blobs/coral.png +0 -0
  547. package/src/interfaces/web/public/modules/blobs/cubi.png +0 -0
  548. package/src/interfaces/web/public/modules/blobs/eclipse.png +0 -0
  549. package/src/interfaces/web/public/modules/blobs/faro.png +0 -0
  550. package/src/interfaces/web/public/modules/blobs/gajo.png +0 -0
  551. package/src/interfaces/web/public/modules/blobs/iris.png +0 -0
  552. package/src/interfaces/web/public/modules/blobs/kiwi.png +0 -0
  553. package/src/interfaces/web/public/modules/blobs/laguna.png +0 -0
  554. package/src/interfaces/web/public/modules/blobs/lila.png +0 -0
  555. package/src/interfaces/web/public/modules/blobs/menta.png +0 -0
  556. package/src/interfaces/web/public/modules/blobs/nimbo.png +0 -0
  557. package/src/interfaces/web/public/modules/blobs/noche.png +0 -0
  558. package/src/interfaces/web/public/modules/blobs/onyx.png +0 -0
  559. package/src/interfaces/web/public/modules/blobs/orbita.png +0 -0
  560. package/src/interfaces/web/public/modules/blobs/ovni.png +0 -0
  561. package/src/interfaces/web/public/modules/blobs/papa.png +0 -0
  562. package/src/interfaces/web/public/modules/blobs/parche.png +0 -0
  563. package/src/interfaces/web/public/modules/blobs/peon.png +0 -0
  564. package/src/interfaces/web/public/modules/blobs/perla.png +0 -0
  565. package/src/interfaces/web/public/modules/blobs/pino.png +0 -0
  566. package/src/interfaces/web/public/modules/blobs/quad.png +0 -0
  567. package/src/interfaces/web/public/modules/blobs/rubi.png +0 -0
  568. package/src/interfaces/web/public/modules/blobs/saturno.png +0 -0
  569. package/src/interfaces/web/public/modules/blobs/trebol.png +0 -0
  570. package/src/interfaces/web/public/modules/blobs/trino.png +0 -0
  571. package/src/interfaces/web/public/modules/blobs/volcan.png +0 -0
  572. package/src/interfaces/web/public/modules/blobs/zafiro.png +0 -0
  573. package/src/interfaces/web/public/sw.js +106 -0
  574. package/src/interfaces/web/src/App.tsx +106 -10
  575. package/src/interfaces/web/src/assets/cli/claude.webp +0 -0
  576. package/src/interfaces/web/src/assets/cli/codex.webp +0 -0
  577. package/src/interfaces/web/src/assets/cli/cursor.svg +1 -0
  578. package/src/interfaces/web/src/assets/cli/opencode.png +0 -0
  579. package/src/interfaces/web/src/components/Combobox.tsx +201 -0
  580. package/src/interfaces/web/src/components/MobileHint.tsx +95 -0
  581. package/src/interfaces/web/src/components/MobileLinkDialog.tsx +156 -0
  582. package/src/interfaces/web/src/components/ModelCombobox.tsx +21 -113
  583. package/src/interfaces/web/src/components/{routines/ReadOnlyBlock.tsx → ReadOnlyBlock.tsx} +13 -4
  584. package/src/interfaces/web/src/components/Roby.tsx +5 -3
  585. package/src/interfaces/web/src/components/RobyBubble.tsx +23 -5
  586. package/src/interfaces/web/src/components/RowMenu.tsx +46 -0
  587. package/src/interfaces/web/src/components/TimezoneSelect.tsx +4 -1
  588. package/src/interfaces/web/src/components/Toast.tsx +50 -14
  589. package/src/interfaces/web/src/components/UiSelect.tsx +12 -5
  590. package/src/interfaces/web/src/components/agents/AgentAvatar.tsx +171 -0
  591. package/src/interfaces/web/src/components/agents/AgentFormFields.tsx +42 -11
  592. package/src/interfaces/web/src/components/agents/AgentModelBadge.tsx +157 -0
  593. package/src/interfaces/web/src/components/agents/AgentModelSelect.tsx +57 -0
  594. package/src/interfaces/web/src/components/agents/AgentSkillsPicker.tsx +115 -0
  595. package/src/interfaces/web/src/components/agents/BlobAvatar.tsx +50 -0
  596. package/src/interfaces/web/src/components/agents/blobPresets.ts +50 -0
  597. package/src/interfaces/web/src/components/agents/modelCatalog.ts +66 -0
  598. package/src/interfaces/web/src/components/chat/ActionGroup.tsx +162 -0
  599. package/src/interfaces/web/src/components/chat/AskAnswersCard.tsx +4 -3
  600. package/src/interfaces/web/src/components/chat/AskQuestionsCard.tsx +1 -1
  601. package/src/interfaces/web/src/components/chat/Attachment.tsx +220 -0
  602. package/src/interfaces/web/src/components/chat/ChatList.tsx +226 -51
  603. package/src/interfaces/web/src/components/chat/ChatRowActivity.tsx +45 -0
  604. package/src/interfaces/web/src/components/chat/Composer.tsx +672 -23
  605. package/src/interfaces/web/src/components/chat/ComposerCommands.tsx +175 -0
  606. package/src/interfaces/web/src/components/chat/ComposerSuggest.tsx +215 -0
  607. package/src/interfaces/web/src/components/chat/ContextBar.tsx +133 -65
  608. package/src/interfaces/web/src/components/chat/InlineAskPanel.tsx +107 -47
  609. package/src/interfaces/web/src/components/chat/MessageBubble.tsx +460 -119
  610. package/src/interfaces/web/src/components/chat/MessageList.tsx +165 -18
  611. package/src/interfaces/web/src/components/chat/ReasoningBlock.tsx +58 -0
  612. package/src/interfaces/web/src/components/chat/SessionPicker.tsx +182 -0
  613. package/src/interfaces/web/src/components/chat/SkillTrace.tsx +183 -0
  614. package/src/interfaces/web/src/components/chat/ToolCall.tsx +11 -11
  615. package/src/interfaces/web/src/components/code/CodeContextTab.tsx +87 -53
  616. package/src/interfaces/web/src/components/code/CodeFileTree.tsx +11 -52
  617. package/src/interfaces/web/src/components/code/CodeFileViewer.tsx +5 -4
  618. package/src/interfaces/web/src/components/code/CodeProjectPicker.tsx +31 -7
  619. package/src/interfaces/web/src/components/code/CodeSessionList.tsx +32 -11
  620. package/src/interfaces/web/src/components/code/CodeSidePanel.tsx +33 -3
  621. package/src/interfaces/web/src/components/code/CodeTerminal.tsx +5 -4
  622. package/src/interfaces/web/src/components/code/NewCodeSessionDialog.tsx +164 -0
  623. package/src/interfaces/web/src/components/commitments/CommitmentDetail.tsx +162 -0
  624. package/src/interfaces/web/src/components/commitments/CommitmentFormDialog.tsx +158 -0
  625. package/src/interfaces/web/src/components/commitments/CommitmentList.tsx +194 -0
  626. package/src/interfaces/web/src/components/commitments/commitmentState.tsx +46 -0
  627. package/src/interfaces/web/src/components/common/BulkActionBar.tsx +60 -0
  628. package/src/interfaces/web/src/components/common/ConfirmDialog.tsx +4 -1
  629. package/src/interfaces/web/src/components/common/SelectCheckbox.tsx +40 -0
  630. package/src/interfaces/web/src/components/common/TabNav.tsx +1 -1
  631. package/src/interfaces/web/src/components/cron/CronPicker.tsx +1 -1
  632. package/src/interfaces/web/src/components/files/FileBrowser.tsx +1 -1
  633. package/src/interfaces/web/src/components/files/FileTree.tsx +6 -4
  634. package/src/interfaces/web/src/components/files/FileViewer.tsx +9 -5
  635. package/src/interfaces/web/src/components/files/MarkdownPreview.tsx +45 -9
  636. package/src/interfaces/web/src/components/images/ImageDefaultsCard.tsx +93 -0
  637. package/src/interfaces/web/src/components/images/ImageProviderList.tsx +142 -0
  638. package/src/interfaces/web/src/components/images/ImageProviderModal.tsx +263 -0
  639. package/src/interfaces/web/src/components/images/ImageTestCard.tsx +142 -0
  640. package/src/interfaces/web/src/components/inbox/ChannelFilter.tsx +178 -0
  641. package/src/interfaces/web/src/components/inbox/InboxList.tsx +77 -81
  642. package/src/interfaces/web/src/components/inbox/InboxRowItem.tsx +140 -0
  643. package/src/interfaces/web/src/components/integrations/ComingSoonPlugin.tsx +2 -2
  644. package/src/interfaces/web/src/components/integrations/PluginConnect.tsx +208 -30
  645. package/src/interfaces/web/src/components/integrations/PluginToolsSection.tsx +1 -1
  646. package/src/interfaces/web/src/components/layout/ProjectAvatar.tsx +39 -24
  647. package/src/interfaces/web/src/components/layout/ProjectSidebar.tsx +253 -58
  648. package/src/interfaces/web/src/components/memory/MemoryBrowser.tsx +94 -47
  649. package/src/interfaces/web/src/components/routines/ExecutionsList.tsx +202 -90
  650. package/src/interfaces/web/src/components/routines/RoutineDetail.tsx +28 -6
  651. package/src/interfaces/web/src/components/routines/RoutineEditor.tsx +16 -5
  652. package/src/interfaces/web/src/components/routines/RoutineList.tsx +49 -9
  653. package/src/interfaces/web/src/components/routines/VarTextarea.tsx +1 -1
  654. package/src/interfaces/web/src/components/routines/runChat.ts +121 -0
  655. package/src/interfaces/web/src/components/sessions/SessionDetail.tsx +148 -0
  656. package/src/interfaces/web/src/components/sessions/SessionTerminal.tsx +98 -0
  657. package/src/interfaces/web/src/components/settings/AccessPanel.tsx +205 -0
  658. package/src/interfaces/web/src/components/settings/DefaultRouterCard.tsx +246 -101
  659. package/src/interfaces/web/src/components/settings/DesktopSettingsPanel.tsx +36 -2
  660. package/src/interfaces/web/src/components/settings/DevicesPanel.tsx +19 -6
  661. package/src/interfaces/web/src/components/settings/EmbedProviderList.tsx +274 -0
  662. package/src/interfaces/web/src/components/settings/EnginesPanel.tsx +26 -6
  663. package/src/interfaces/web/src/components/settings/MemoryPanel.tsx +118 -119
  664. package/src/interfaces/web/src/components/settings/NudgePanel.tsx +4 -3
  665. package/src/interfaces/web/src/components/settings/PairDeviceDialog.tsx +15 -4
  666. package/src/interfaces/web/src/components/settings/PanelPrefs.tsx +374 -0
  667. package/src/interfaces/web/src/components/settings/ProfilePanel.tsx +70 -2
  668. package/src/interfaces/web/src/components/settings/RoutingPanel.tsx +2 -1
  669. package/src/interfaces/web/src/components/settings/SkillsInspectorPanel.tsx +102 -43
  670. package/src/interfaces/web/src/components/settings/SkillsManager.tsx +76 -21
  671. package/src/interfaces/web/src/components/settings/SkillsSettings.tsx +10 -3
  672. package/src/interfaces/web/src/components/settings/SuperAgentPanel.tsx +8 -0
  673. package/src/interfaces/web/src/components/settings/TelegramChannelsPanel.tsx +11 -2
  674. package/src/interfaces/web/src/components/settings/TelegramContactsPanel.tsx +19 -8
  675. package/src/interfaces/web/src/components/settings/TelegramRolesPanel.tsx +12 -2
  676. package/src/interfaces/web/src/components/settings/WebPanel.tsx +22 -31
  677. package/src/interfaces/web/src/components/settings/providers/ProviderCard.tsx +15 -3
  678. package/src/interfaces/web/src/components/settings/providers/ProviderModal.tsx +97 -66
  679. package/src/interfaces/web/src/components/settings/providers/ProviderTestDialog.tsx +150 -0
  680. package/src/interfaces/web/src/components/settings/providers/typeStyles.ts +67 -25
  681. package/src/interfaces/web/src/components/settings/providers/types.ts +3 -0
  682. package/src/interfaces/web/src/components/tasks/TaskBoard.tsx +201 -0
  683. package/src/interfaces/web/src/components/tasks/TaskColumnsDialog.tsx +243 -0
  684. package/src/interfaces/web/src/components/tasks/TaskComments.tsx +167 -0
  685. package/src/interfaces/web/src/components/tasks/TaskDetail.tsx +335 -0
  686. package/src/interfaces/web/src/components/tasks/TaskFormDialog.tsx +406 -0
  687. package/src/interfaces/web/src/components/tasks/TaskList.tsx +258 -0
  688. package/src/interfaces/web/src/components/tasks/TaskSubtasks.tsx +126 -0
  689. package/src/interfaces/web/src/components/tasks/columns.ts +51 -0
  690. package/src/interfaces/web/src/components/tasks/taskStatus.tsx +159 -34
  691. package/src/interfaces/web/src/components/tasks/taskViewPrefs.ts +73 -0
  692. package/src/interfaces/web/src/components/tasks/useTaskColumns.ts +31 -0
  693. package/src/interfaces/web/src/components/ui/chat-input.tsx +136 -12
  694. package/src/interfaces/web/src/components/ui/context-menu.tsx +15 -198
  695. package/src/interfaces/web/src/components/ui/dialog.tsx +3 -2
  696. package/src/interfaces/web/src/components/ui/filter-chips.tsx +4 -0
  697. package/src/interfaces/web/src/components/ui/popover.tsx +14 -49
  698. package/src/interfaces/web/src/components/ui/sheet.tsx +2 -1
  699. package/src/interfaces/web/src/components/ui/spinner.tsx +2 -1
  700. package/src/interfaces/web/src/components/ui.tsx +62 -23
  701. package/src/interfaces/web/src/components/voice/VoiceProviderList.tsx +2 -1
  702. package/src/interfaces/web/src/components/voice/VoiceProviderModal.tsx +66 -8
  703. package/src/interfaces/web/src/components/voice/VoiceQvoxInstallCard.tsx +63 -0
  704. package/src/interfaces/web/src/components/voice/VoiceQvoxStatusCard.tsx +51 -0
  705. package/src/interfaces/web/src/components/voice/VoiceSttCard.tsx +4 -3
  706. package/src/interfaces/web/src/components/voice/VoiceTestCard.tsx +38 -4
  707. package/src/interfaces/web/src/constants/index.ts +1 -0
  708. package/src/interfaces/web/src/hooks/useChannelPrefs.ts +39 -0
  709. package/src/interfaces/web/src/hooks/useChat.ts +1092 -85
  710. package/src/interfaces/web/src/hooks/useChatActivity.ts +24 -0
  711. package/src/interfaces/web/src/hooks/useInbox.ts +26 -4
  712. package/src/interfaces/web/src/hooks/useLiveMessages.ts +16 -0
  713. package/src/interfaces/web/src/hooks/useOllamaModels.ts +79 -0
  714. package/src/interfaces/web/src/hooks/useRecorder.ts +198 -0
  715. package/src/interfaces/web/src/hooks/useTokenBootstrap.ts +23 -6
  716. package/src/interfaces/web/src/i18n/en.ts +832 -175
  717. package/src/interfaces/web/src/i18n/es.ts +841 -188
  718. package/src/interfaces/web/src/lib/api/agents.ts +23 -4
  719. package/src/interfaces/web/src/lib/api/code.ts +17 -0
  720. package/src/interfaces/web/src/lib/api/commitments.ts +7 -1
  721. package/src/interfaces/web/src/lib/api/conversations.ts +38 -11
  722. package/src/interfaces/web/src/lib/api/embeddings.ts +3 -0
  723. package/src/interfaces/web/src/lib/api/engines.ts +14 -0
  724. package/src/interfaces/web/src/lib/api/groups.ts +93 -0
  725. package/src/interfaces/web/src/lib/api/images.ts +193 -0
  726. package/src/interfaces/web/src/lib/api/inbox.ts +29 -5
  727. package/src/interfaces/web/src/lib/api/integrations.ts +9 -0
  728. package/src/interfaces/web/src/lib/api/media.ts +126 -0
  729. package/src/interfaces/web/src/lib/api/net.ts +44 -0
  730. package/src/interfaces/web/src/lib/api/profiles.ts +12 -0
  731. package/src/interfaces/web/src/lib/api/projects.ts +9 -1
  732. package/src/interfaces/web/src/lib/api/routines.ts +9 -1
  733. package/src/interfaces/web/src/lib/api/sessions.ts +18 -0
  734. package/src/interfaces/web/src/lib/api/skills.ts +8 -0
  735. package/src/interfaces/web/src/lib/api/super_agent.ts +3 -0
  736. package/src/interfaces/web/src/lib/api/tasks.ts +46 -6
  737. package/src/interfaces/web/src/lib/api/tools.ts +2 -0
  738. package/src/interfaces/web/src/lib/api/transcribe.ts +31 -0
  739. package/src/interfaces/web/src/lib/api/turns.ts +20 -0
  740. package/src/interfaces/web/src/lib/api/voice.ts +72 -2
  741. package/src/interfaces/web/src/lib/api.ts +3 -0
  742. package/src/interfaces/web/src/lib/channels.ts +214 -0
  743. package/src/interfaces/web/src/lib/chat-activity.ts +175 -0
  744. package/src/interfaces/web/src/lib/chat-prefs.ts +48 -0
  745. package/src/interfaces/web/src/lib/code-context.ts +0 -2
  746. package/src/interfaces/web/src/lib/http.ts +51 -17
  747. package/src/interfaces/web/src/lib/inbox-selection.ts +29 -0
  748. package/src/interfaces/web/src/lib/live.ts +252 -0
  749. package/src/interfaces/web/src/lib/net.ts +211 -0
  750. package/src/interfaces/web/src/lib/notify.ts +331 -0
  751. package/src/interfaces/web/src/lib/projectNav.ts +40 -0
  752. package/src/interfaces/web/src/lib/pwa.ts +115 -0
  753. package/src/interfaces/web/src/lib/qvox.ts +24 -0
  754. package/src/interfaces/web/src/lib/slug.ts +3 -0
  755. package/src/interfaces/web/src/lib/tone.ts +150 -0
  756. package/src/interfaces/web/src/main.tsx +15 -4
  757. package/src/interfaces/web/src/screens/ApxAdminScreen.tsx +33 -11
  758. package/src/interfaces/web/src/screens/InboxScreen.tsx +126 -71
  759. package/src/interfaces/web/src/screens/ProjectScreen.tsx +8 -4
  760. package/src/interfaces/web/src/screens/SettingsScreen.tsx +7 -4
  761. package/src/interfaces/web/src/screens/base/AgentDefaultsTab.tsx +30 -9
  762. package/src/interfaces/web/src/screens/base/CommitmentsTab.tsx +150 -168
  763. package/src/interfaces/web/src/screens/base/LogsTab.tsx +8 -7
  764. package/src/interfaces/web/src/screens/base/SessionsTab.tsx +99 -37
  765. package/src/interfaces/web/src/screens/base/WorkspacesTab.tsx +1 -1
  766. package/src/interfaces/web/src/screens/mobile/MobileChat.tsx +85 -0
  767. package/src/interfaces/web/src/screens/mobile/MobileChatList.tsx +244 -0
  768. package/src/interfaces/web/src/screens/mobile/MobileCommitments.tsx +350 -0
  769. package/src/interfaces/web/src/screens/mobile/MobileScreen.tsx +138 -0
  770. package/src/interfaces/web/src/screens/mobile/MobileTabBar.tsx +105 -0
  771. package/src/interfaces/web/src/screens/mobile/MobileTasks.tsx +407 -0
  772. package/src/interfaces/web/src/screens/mobile/NewChatSheet.tsx +313 -0
  773. package/src/interfaces/web/src/screens/mobile/mobileList.tsx +194 -0
  774. package/src/interfaces/web/src/screens/mobile/routes.ts +239 -0
  775. package/src/interfaces/web/src/screens/modules/CodeScreen.tsx +135 -64
  776. package/src/interfaces/web/src/screens/modules/DeckScreen.tsx +0 -1
  777. package/src/interfaces/web/src/screens/modules/ImagesScreen.tsx +172 -0
  778. package/src/interfaces/web/src/screens/modules/VoiceScreen.tsx +36 -4
  779. package/src/interfaces/web/src/screens/project/AgentBrainGraph.tsx +117 -30
  780. package/src/interfaces/web/src/screens/project/AgentDetailScreen.tsx +537 -92
  781. package/src/interfaces/web/src/screens/project/AgentsTab.tsx +344 -93
  782. package/src/interfaces/web/src/screens/project/ArtifactsTab.tsx +1 -1
  783. package/src/interfaces/web/src/screens/project/ChatTab.tsx +1160 -94
  784. package/src/interfaces/web/src/screens/project/IntegrationsTab.tsx +3 -2
  785. package/src/interfaces/web/src/screens/project/McpsTab.tsx +62 -14
  786. package/src/interfaces/web/src/screens/project/Overview.tsx +36 -15
  787. package/src/interfaces/web/src/screens/project/RoutinesTab.tsx +93 -8
  788. package/src/interfaces/web/src/screens/project/SkillsTab.tsx +4 -1
  789. package/src/interfaces/web/src/screens/project/StructureTab.tsx +5 -4
  790. package/src/interfaces/web/src/screens/project/TasksTab.tsx +351 -129
  791. package/src/interfaces/web/src/screens/project/VarsTab.tsx +17 -5
  792. package/src/interfaces/web/src/styles.css +106 -31
  793. package/src/interfaces/web/src/types/daemon.ts +246 -2
  794. package/src/interfaces/web/src/vite-env.d.ts +20 -0
  795. package/src/interfaces/tui/plugin/command-shim.ts +0 -109
  796. package/src/interfaces/web/components.json +0 -25
  797. package/src/interfaces/web/dist/assets/index-CvEoGtTf.js +0 -849
  798. package/src/interfaces/web/dist/assets/index-CvEoGtTf.js.map +0 -1
  799. package/src/interfaces/web/dist/assets/index-DzBBXFaO.css +0 -1
  800. package/src/interfaces/web/src/components/tasks/TaskDetailPanel.tsx +0 -142
  801. package/src/interfaces/web/src/components/ui/accordion.tsx +0 -72
  802. package/src/interfaces/web/src/components/ui/alert-dialog.tsx +0 -187
  803. package/src/interfaces/web/src/components/ui/alert.tsx +0 -76
  804. package/src/interfaces/web/src/components/ui/aspect-ratio.tsx +0 -22
  805. package/src/interfaces/web/src/components/ui/avatar.tsx +0 -107
  806. package/src/interfaces/web/src/components/ui/breadcrumb.tsx +0 -125
  807. package/src/interfaces/web/src/components/ui/button-group.tsx +0 -87
  808. package/src/interfaces/web/src/components/ui/calendar.tsx +0 -221
  809. package/src/interfaces/web/src/components/ui/card.tsx +0 -103
  810. package/src/interfaces/web/src/components/ui/carousel.tsx +0 -242
  811. package/src/interfaces/web/src/components/ui/chart.tsx +0 -371
  812. package/src/interfaces/web/src/components/ui/checkbox.tsx +0 -29
  813. package/src/interfaces/web/src/components/ui/collapsible.tsx +0 -19
  814. package/src/interfaces/web/src/components/ui/combobox.tsx +0 -295
  815. package/src/interfaces/web/src/components/ui/command.tsx +0 -196
  816. package/src/interfaces/web/src/components/ui/direction.tsx +0 -4
  817. package/src/interfaces/web/src/components/ui/drawer.tsx +0 -134
  818. package/src/interfaces/web/src/components/ui/empty.tsx +0 -104
  819. package/src/interfaces/web/src/components/ui/field.tsx +0 -236
  820. package/src/interfaces/web/src/components/ui/hover-card.tsx +0 -51
  821. package/src/interfaces/web/src/components/ui/input-otp.tsx +0 -85
  822. package/src/interfaces/web/src/components/ui/item.tsx +0 -201
  823. package/src/interfaces/web/src/components/ui/menubar.tsx +0 -280
  824. package/src/interfaces/web/src/components/ui/native-select.tsx +0 -61
  825. package/src/interfaces/web/src/components/ui/navigation-menu.tsx +0 -168
  826. package/src/interfaces/web/src/components/ui/pagination.tsx +0 -130
  827. package/src/interfaces/web/src/components/ui/progress.tsx +0 -83
  828. package/src/interfaces/web/src/components/ui/radio-group.tsx +0 -36
  829. package/src/interfaces/web/src/components/ui/resizable.tsx +0 -50
  830. package/src/interfaces/web/src/components/ui/scroll-area.tsx +0 -53
  831. package/src/interfaces/web/src/components/ui/sidebar.tsx +0 -726
  832. package/src/interfaces/web/src/components/ui/slider.tsx +0 -52
  833. package/src/interfaces/web/src/components/ui/sonner.tsx +0 -49
  834. package/src/interfaces/web/src/components/ui/table.tsx +0 -116
  835. package/src/interfaces/web/src/components/ui/toggle-group.tsx +0 -87
  836. package/src/interfaces/web/src/components/ui/toggle.tsx +0 -45
  837. package/src/interfaces/web/src/hooks/use-mobile.ts +0 -19
  838. package/src/interfaces/web/src/screens/base/GlobalTasksTab.tsx +0 -161
@@ -3,12 +3,22 @@
3
3
  // GET /projects/:pid/tasks ?state=open|done|dropped|all&tag=X&agent=Y
4
4
  // &due_before=ISO&due_after=ISO&limit=N
5
5
  // &status=pending|running|in_review|blocked&updated_since=ISO
6
- // POST /projects/:pid/tasks { title, body?, tags?, due?, agent?, source?, meta? }
6
+ // POST /projects/:pid/tasks { title, description?, body?, tags?, due?,
7
+ // agent?, source?, meta? }
7
8
  // GET /projects/:pid/tasks/:id (id or prefix)
8
9
  // PATCH /projects/:pid/tasks/:id { patch: {...} }
9
10
  // POST /projects/:pid/tasks/:id/done { by? }
10
11
  // POST /projects/:pid/tasks/:id/drop { by? }
11
12
  // POST /projects/:pid/tasks/:id/reopen
13
+ // POST /projects/:pid/tasks/:id/comments { text, by? } — @mentions summon agents
14
+ // GET /tasks/columns the GLOBAL board-column catalog
15
+ // PUT /tasks/columns { columns: [{id,label?}] }
16
+ // GET /projects/:pid/tasks/columns { columns, catalog } for that project
17
+ // PUT /projects/:pid/tasks/columns { columns: [id] } — a subset of the catalog
18
+ //
19
+ // `?parent=<id>` on either list route returns that task's SUBTASKS; `?parent=`
20
+ // (empty) returns only top-level tasks. A subtask is a task with a parent, so
21
+ // every verb above works on one unchanged.
12
22
  import {
13
23
  createTask,
14
24
  listTasks,
@@ -20,16 +30,47 @@ import {
20
30
  reopenTask,
21
31
  setTaskStatus,
22
32
  countTasks,
23
- TASK_STATUSES,
24
33
  } from "#core/stores/tasks.js";
34
+ import { addComment } from "#core/stores/tasks.js";
35
+ import { readConfig, writeConfig } from "#core/config/index.js";
36
+ import {
37
+ DONE_COLUMN, columnHook, normalizeColumns, isColumnId, projectColumns, readColumnCatalog,
38
+ } from "#core/tasks/columns.js";
39
+ import { readAgents } from "#core/apc/parser.js";
40
+ import { readProjectConfig, writeProjectConfig } from "../project-config.js";
41
+ import { mentionedAgents, runCommentMentions } from "#core/tasks/comment-turn.js";
42
+ import { OWNER_ACTOR_ID } from "#core/constants/actors.js";
25
43
  import { pageEnvelope } from "./shared.js";
26
44
 
27
- export function register(api, { project, projects }) {
45
+ /** What the board says when a column has an agent but no instruction. */
46
+ function defaultHookLine(label) {
47
+ return `esta task pasó a "${label}". Hacé lo que corresponda y dejá el resultado acá.`;
48
+ }
49
+
50
+ /**
51
+ * Is this column's agent already working on this task?
52
+ *
53
+ * The newest comment being an owner-authored summon of that same agent means we
54
+ * asked and nothing has come back yet — the moment the agent replies, ITS
55
+ * comment is the newest one and a genuine re-run is allowed again. Without this,
56
+ * dragging a card out of a column and back in (a thing people do constantly)
57
+ * starts a second paid run on top of the first.
58
+ *
59
+ * Matching on `mentions` rather than on the text: the summon line is the
60
+ * column's own instruction when it has one, so there is no wording to look for.
61
+ */
62
+ function hookAlreadyRunning(task, agent) {
63
+ const last = task.comments?.[task.comments.length - 1];
64
+ if (!last) return false;
65
+ return last.by === OWNER_ACTOR_ID && (last.mentions || []).includes(agent);
66
+ }
67
+
68
+ export function register(api, { project, projects, config, plugins, registries }) {
28
69
  // Global tasks across every project, newest first. Returns a { meta, data }
29
70
  // envelope. Paginated via ?limit & ?offset; with no limit, data is the full
30
71
  // set as one page.
31
72
  api.get("/tasks", (req, res) => {
32
- const { state, tag, agent, due_before, due_after, status, updated_since } = req.query;
73
+ const { state, tag, agent, due_before, due_after, status, updated_since, parent } = req.query;
33
74
 
34
75
  // Resolve the registered projects to what core needs, dropping any the
35
76
  // manager can no longer open.
@@ -46,13 +87,17 @@ export function register(api, { project, projects }) {
46
87
  }
47
88
 
48
89
  const { tasks, skipped } = listTasksAcrossProjects(entries, {
49
- state: state === "all" ? undefined : (state || "open"),
90
+ // "all" is passed THROUGH, not turned into undefined: listTasks reads a
91
+ // missing state as "open only", so mapping all→undefined made the
92
+ // aggregated view's All chip show exactly the same rows as Open.
93
+ state: state || "open",
50
94
  tag: tag || undefined,
51
95
  agent: agent || undefined,
52
96
  due_before: due_before || undefined,
53
97
  due_after: due_after || undefined,
54
98
  status: status || undefined,
55
99
  updated_since: updated_since || undefined,
100
+ ...(parent !== undefined ? { parent } : {}),
56
101
  });
57
102
 
58
103
  const envelope = pageEnvelope(tasks, req.query);
@@ -61,12 +106,67 @@ export function register(api, { project, projects }) {
61
106
  res.json(envelope);
62
107
  });
63
108
 
109
+ // The vocabulary every board shares. Editing it here renames/adds/removes a
110
+ // column for every project at once, which is the point: "QA" has to mean the
111
+ // same thing everywhere or an agent told to move something to QA has to ask
112
+ // which one. What each project SHOWS is the per-project route below.
113
+ api.get("/tasks/columns", (_req, res) => {
114
+ res.json({ columns: readColumnCatalog(readConfig()) });
115
+ });
116
+
117
+ api.put("/tasks/columns", (req, res) => {
118
+ const { columns } = req.body || {};
119
+ if (!Array.isArray(columns) || columns.length === 0) {
120
+ return res.status(400).json({ error: "columns must be a non-empty array" });
121
+ }
122
+ const bad = columns.find((c) => !isColumnId(typeof c === "string" ? c : c?.id));
123
+ if (bad) {
124
+ return res.status(400).json({
125
+ error: `invalid column id: ${JSON.stringify(typeof bad === "string" ? bad : bad?.id)} ` +
126
+ `(lowercase letters, digits, - and _; "${DONE_COLUMN}" is reserved)`,
127
+ });
128
+ }
129
+ const cfg = readConfig();
130
+ const next = normalizeColumns(columns);
131
+ writeConfig({ ...cfg, tasks: { ...(cfg.tasks || {}), columns: next } });
132
+ res.json({ columns: next });
133
+ });
134
+
135
+ // What THIS project shows, in order, with `done` appended — plus the catalog
136
+ // it may pick from, so the editor needs one request instead of two.
137
+ api.get("/projects/:pid/tasks/columns", (req, res) => {
138
+ const p = project(req, res);
139
+ if (!p) return;
140
+ const global = readConfig();
141
+ res.json({
142
+ columns: projectColumns(global, readProjectConfig(p.path)),
143
+ catalog: readColumnCatalog(global),
144
+ });
145
+ });
146
+
147
+ api.put("/projects/:pid/tasks/columns", (req, res) => {
148
+ const p = project(req, res);
149
+ if (!p) return;
150
+ const { columns } = req.body || {};
151
+ if (!Array.isArray(columns)) return res.status(400).json({ error: "columns must be an array" });
152
+ const global = readConfig();
153
+ const known = new Set(readColumnCatalog(global).map((c) => c.id));
154
+ const picked = [...new Set(columns.map((c) => String(c?.id || c || "").trim().toLowerCase()))]
155
+ .filter((id) => known.has(id));
156
+ const cfg = readProjectConfig(p.path);
157
+ writeProjectConfig(p.path, { ...cfg, tasks: { ...(cfg.tasks || {}), columns: picked } });
158
+ res.json({
159
+ columns: projectColumns(global, readProjectConfig(p.path)),
160
+ catalog: readColumnCatalog(global),
161
+ });
162
+ });
163
+
64
164
  // Per-project tasks. Returns a { meta, data } envelope; with no ?limit the
65
165
  // data array is the full filtered set (one page).
66
166
  api.get("/projects/:pid/tasks", (req, res) => {
67
167
  const p = project(req, res);
68
168
  if (!p) return;
69
- const { state, tag, agent, due_before, due_after, status, updated_since } = req.query;
169
+ const { state, tag, agent, due_before, due_after, status, updated_since, parent } = req.query;
70
170
  const all = listTasks(p.storagePath, {
71
171
  state: state || undefined,
72
172
  tag: tag || undefined,
@@ -75,6 +175,7 @@ export function register(api, { project, projects }) {
75
175
  due_after: due_after || undefined,
76
176
  status: status || undefined,
77
177
  updated_since: updated_since || undefined,
178
+ ...(parent !== undefined ? { parent } : {}),
78
179
  });
79
180
  res.json(pageEnvelope(all, req.query));
80
181
  });
@@ -136,18 +237,87 @@ export function register(api, { project, projects }) {
136
237
  res.json(updated);
137
238
  });
138
239
 
139
- // Move an open task through its workflow (pending running in_review …).
240
+ // Move an open task to a column. The valid set is the project's own columns
241
+ // (core/tasks/columns.js) — not the four built-ins, which are only the default
242
+ // catalog. `done` is not among them: closing a task is POST …/done, and a
243
+ // board that let you *set* done would leave state and status disagreeing.
140
244
  api.post("/projects/:pid/tasks/:id/status", (req, res) => {
141
245
  const p = project(req, res);
142
246
  if (!p) return;
143
247
  const { status } = req.body || {};
144
- if (!TASK_STATUSES.includes(status))
145
- return res.status(400).json({ error: `status must be one of ${TASK_STATUSES.join(", ")}` });
146
- const updated = setTaskStatus(p.storagePath, req.params.id, status);
248
+ const columns = projectColumns(readConfig(), readProjectConfig(p.path));
249
+ const statuses = columns.map((c) => c.id).filter((id) => id !== DONE_COLUMN);
250
+ if (!statuses.includes(status)) {
251
+ return res.status(400).json({ error: `status must be one of ${statuses.join(", ")}` });
252
+ }
253
+ const updated = setTaskStatus(p.storagePath, req.params.id, status, { statuses });
147
254
  if (!updated) return res.status(404).json({ error: "task not found" });
255
+
256
+ // Column automation: dropping a card in a column that has one hands the task
257
+ // to an agent. It runs through the SAME path a human @mention takes — the
258
+ // handover is written into the thread first, so the board never does
259
+ // anything invisible, and the reply comes back as a comment under the same
260
+ // ceiling. Fire-and-forget: a real QA run takes as long as the QA takes.
261
+ const hook = columnHook(columns, status);
262
+ if (hook && !hookAlreadyRunning(updated, hook.agent)) {
263
+ let hasAgent = false;
264
+ try { hasAgent = readAgents(p.path).some((a) => a.slug === hook.agent); } catch { hasAgent = false; }
265
+ if (hasAgent) {
266
+ const label = columns.find((c) => c.id === status)?.label || status;
267
+ const text = hook.instruction
268
+ ? `@${hook.agent} ${hook.instruction}`
269
+ : `@${hook.agent} ${defaultHookLine(label)}`;
270
+ try {
271
+ addComment(p.storagePath, updated.id, {
272
+ by: OWNER_ACTOR_ID, text, mentions: [hook.agent],
273
+ });
274
+ runCommentMentions({
275
+ p, taskId: updated.id, seed: [hook.agent], author: OWNER_ACTOR_ID,
276
+ projects, plugins, registries, config,
277
+ }).catch(() => { /* the failure is written into the thread */ });
278
+ } catch { /* a broken hook must not fail the move */ }
279
+ }
280
+ }
281
+
148
282
  res.json(updated);
149
283
  });
150
284
 
285
+ // Add a comment. @-mentioning an agent hands it the task: it runs a REAL turn
286
+ // with its own tools and writes back another comment (core/tasks/comment-turn).
287
+ //
288
+ // The cascade is NOT awaited. An agent doing actual QA takes as long as the QA
289
+ // takes, and a request that hangs for it would time out on the phone and be
290
+ // retried into a second run. The comment is persisted before we answer, so the
291
+ // 201 is honest about what exists; the replies arrive in the thread after.
292
+ api.post("/projects/:pid/tasks/:id/comments", (req, res) => {
293
+ const p = project(req, res);
294
+ if (!p) return;
295
+ const { text, by = OWNER_ACTOR_ID } = req.body || {};
296
+ if (typeof text !== "string" || !text.trim()) {
297
+ return res.status(400).json({ error: "text required" });
298
+ }
299
+
300
+ // Resolved here, not in the store: the roster lives with the project and
301
+ // the thread should record who was actually reachable on the day.
302
+ const mentions = mentionedAgents(text, p.path, by);
303
+ let task;
304
+ try {
305
+ task = addComment(p.storagePath, req.params.id, { by, text, mentions });
306
+ } catch (e) {
307
+ return res.status(400).json({ error: e.message });
308
+ }
309
+ if (!task) return res.status(404).json({ error: "task not found" });
310
+
311
+ if (mentions.length) {
312
+ runCommentMentions({
313
+ p, taskId: task.id, seed: mentions, author: by,
314
+ projects, plugins, registries, config,
315
+ }).catch(() => { /* the failure is already written into the thread */ });
316
+ }
317
+
318
+ res.status(201).json({ task, summoned: mentions });
319
+ });
320
+
151
321
  // Lightweight summary endpoint for status displays.
152
322
  api.get("/projects/:pid/tasks-summary", (req, res) => {
153
323
  const p = project(req, res);
@@ -44,6 +44,7 @@ import {
44
44
 
45
45
  import { redactChannel, isSecretMarker } from "#core/config/redact.js";
46
46
  import { canNudge, recordNudge, nudgeFeedbackKeyboard } from "#core/nudge/index.js";
47
+ import { asyncRoute } from "./shared.js";
47
48
 
48
49
  export function register(api, { telegram }) {
49
50
  api.get("/telegram/status", (_req, res) => {
@@ -73,7 +74,7 @@ export function register(api, { telegram }) {
73
74
  }
74
75
  });
75
76
 
76
- api.post("/telegram/send", async (req, res) => {
77
+ api.post("/telegram/send", asyncRoute(async (req, res) => {
77
78
  const { chat_id, text, channel } = req.body || {};
78
79
  if (!text) return res.status(400).json({ error: "text required" });
79
80
  if (!telegram)
@@ -84,9 +85,9 @@ export function register(api, { telegram }) {
84
85
  } catch (e) {
85
86
  res.status(502).json({ error: e.message });
86
87
  }
87
- });
88
+ }));
88
89
 
89
- api.post("/telegram/send_photo", async (req, res) => {
90
+ api.post("/telegram/send_photo", asyncRoute(async (req, res) => {
90
91
  const { chat_id, photo, caption, parse_mode, channel } = req.body || {};
91
92
  if (!photo)
92
93
  return res.status(400).json({ error: "photo required (path or url)" });
@@ -104,9 +105,9 @@ export function register(api, { telegram }) {
104
105
  } catch (e) {
105
106
  res.status(502).json({ error: e.message });
106
107
  }
107
- });
108
+ }));
108
109
 
109
- api.post("/telegram/send_voice", async (req, res) => {
110
+ api.post("/telegram/send_voice", asyncRoute(async (req, res) => {
110
111
  const { chat_id, audio, caption, duration, channel } = req.body || {};
111
112
  if (!audio) return res.status(400).json({ error: "audio required (path)" });
112
113
  if (!telegram)
@@ -123,9 +124,9 @@ export function register(api, { telegram }) {
123
124
  } catch (e) {
124
125
  res.status(502).json({ error: e.message });
125
126
  }
126
- });
127
+ }));
127
128
 
128
- api.post("/telegram/send_audio", async (req, res) => {
129
+ api.post("/telegram/send_audio", asyncRoute(async (req, res) => {
129
130
  const { chat_id, audio, caption, title, performer, channel } =
130
131
  req.body || {};
131
132
  if (!audio) return res.status(400).json({ error: "audio required (path)" });
@@ -144,7 +145,7 @@ export function register(api, { telegram }) {
144
145
  } catch (e) {
145
146
  res.status(502).json({ error: e.message });
146
147
  }
147
- });
148
+ }));
148
149
 
149
150
  // ── Channel CRUD (config-only; caller must POST /admin/reload to apply) ──
150
151
  // We read fresh config from disk on each call so concurrent writes from the
@@ -309,7 +310,7 @@ export function register(api, { telegram }) {
309
310
  // interruption budget applies by default. A caller delivering something the
310
311
  // user is waiting for says so with `unsolicited: false`, and that choice is
311
312
  // then visible in its own diff rather than hidden in this handler.
312
- api.post("/telegram/notify", async (req, res) => {
313
+ api.post("/telegram/notify", asyncRoute(async (req, res) => {
313
314
  const { chat_id, text, channel, kind, project_id, severity, unsolicited } = req.body || {};
314
315
  if (!text) return res.status(400).json({ error: "text required" });
315
316
  if (!telegram)
@@ -348,5 +349,5 @@ export function register(api, { telegram }) {
348
349
  } catch (e) {
349
350
  res.status(502).json({ error: e.message });
350
351
  }
351
- });
352
+ }));
352
353
  }
@@ -0,0 +1,159 @@
1
+ // Who is in a multi-agent thread, and what that thread is CALLED.
2
+ //
3
+ // An a2a or group thread is a conversation BETWEEN agents, so every surface
4
+ // that shows one — the inbox rows, the Chats sidebar, the thread header on the
5
+ // desktop and on the phone — has to answer the same two questions: which faces
6
+ // to draw, and what name to put on it. There was no single answer: the inbox
7
+ // resolved both here in the API, the sidebar re-derived faces in React from its
8
+ // own agent list, and the thread header could only do it when the inbox handed
9
+ // it the row it had already resolved. Same ledger, three resolutions, two of
10
+ // them incomplete — which is why `/inbox` drew "Andy · OpenCode" with both
11
+ // avatars while `/p/0/chat` drew the same thread as a faceless `andy~opencode`.
12
+ //
13
+ // So it is answered ONCE, here, and travels ON the payload: `participant_faces`
14
+ // plus a resolved `title`. Every frontend renders what it is given; none of them
15
+ // re-derives a face from a slug.
16
+ //
17
+ // It lives at the surface rather than in core because the super-agent's display
18
+ // name comes from identity.json and core must not reach for it (rule 4).
19
+ import { readAgents } from "#core/apc/parser.js";
20
+ import { resolveSuperAgentBlob } from "#core/apc/agent-identity.js";
21
+ import { readConfig } from "#core/config/index.js";
22
+ import { resolveAgentName, SUPERAGENT_ACTOR_ID } from "#core/identity/index.js";
23
+
24
+ const LEGACY_SUPER_AGENT_SLUGS = new Set([
25
+ "default", "superagent", "super-agent", "super_agent", "apx", "roby", "__super_agent__",
26
+ ]);
27
+
28
+ // Coding CLIs aren't project agents (no .apc file, so no face resolves), but an
29
+ // a2a pair with one should read as its brand, not a bare lowercase slug. Keys
30
+ // match the frontend's CLI_LOGOS so the logo still lands (it matches on the
31
+ // lowercased name), the label just wears proper case.
32
+ const CLI_DISPLAY_NAMES = {
33
+ claude: "Claude",
34
+ "claude-code": "Claude",
35
+ codex: "Codex",
36
+ opencode: "OpenCode",
37
+ cursor: "Cursor",
38
+ "cursor-agent": "Cursor",
39
+ aider: "Aider",
40
+ gemini: "Gemini",
41
+ qwen: "Qwen",
42
+ };
43
+
44
+ /** The three display fields an agent carries, from either shape it arrives in. */
45
+ function faceOfAgent(a) {
46
+ return {
47
+ name: a?.fields?.Name || a?.name || null,
48
+ emoji: a?.fields?.Emoji || a?.emoji || null,
49
+ icon: a?.fields?.Icon || a?.icon || null,
50
+ };
51
+ }
52
+
53
+ /** An unreadable AGENTS.md is one project without faces, never a failed request. */
54
+ export function readAgentsSafe(dir) {
55
+ try { return dir ? readAgents(dir) : []; } catch { return []; }
56
+ }
57
+
58
+ /**
59
+ * A resolver for one request: `slug → face`, and `thread → decorated thread`.
60
+ *
61
+ * `projectPaths` are the working-copy paths of every registered project, because
62
+ * an a2a pair can SPAN them — a coding CLI in one project talking to an agent
63
+ * that lives in another. A face looked up only in the thread's own project
64
+ * renders the outsider as a bare letter, so the cross-project index is the
65
+ * fallback. It is built lazily: a request whose participants all live in the
66
+ * caller's own roster never opens another project's AGENTS.md.
67
+ */
68
+ export function createFaceResolver(projectPaths = []) {
69
+ let index = null;
70
+ const globalIndex = () => {
71
+ if (index) return index;
72
+ index = new Map();
73
+ for (const dir of projectPaths) {
74
+ // First project to define a slug wins — collisions are rare, and the
75
+ // caller's own roster is tried before this map anyway.
76
+ for (const a of readAgentsSafe(dir)) if (!index.has(a.slug)) index.set(a.slug, faceOfAgent(a));
77
+ }
78
+ return index;
79
+ };
80
+
81
+ let superFace = null;
82
+ const superAgentFace = () => {
83
+ if (superFace) return superFace;
84
+ let cfg = null;
85
+ try { cfg = readConfig(); } catch { /* no config is not a reason to draw nothing */ }
86
+ // The super-agent is not a project agent, so nothing above resolves it: it
87
+ // needs its persona name and its blob, or an a2a thread it is in renders the
88
+ // bare `super_agent` slug with no avatar.
89
+ superFace = {
90
+ slug: SUPERAGENT_ACTOR_ID,
91
+ name: resolveAgentName(cfg || {}),
92
+ emoji: null,
93
+ icon: resolveSuperAgentBlob(cfg || {}),
94
+ };
95
+ return superFace;
96
+ };
97
+
98
+ /** `localAgents` (the thread's own project roster) wins over every other project. */
99
+ const face = (slug, localAgents = []) => {
100
+ if (slug === SUPERAGENT_ACTOR_ID) return { ...superAgentFace() };
101
+ const local = localAgents.find((a) => a.slug === slug);
102
+ const hit = local ? faceOfAgent(local) : globalIndex().get(slug) || null;
103
+ if (!hit && LEGACY_SUPER_AGENT_SLUGS.has(String(slug).toLowerCase())) {
104
+ return { ...superAgentFace() };
105
+ }
106
+ if (!hit && String(slug).toLowerCase() === "roby-orchestrator") {
107
+ return {
108
+ slug,
109
+ name: "Roby Orchestrator",
110
+ emoji: null,
111
+ icon: superAgentFace().icon,
112
+ };
113
+ }
114
+ return {
115
+ // Physical key, so a surface can OPEN this agent and not just paint it.
116
+ slug,
117
+ // A project agent's own name; else a coding CLI's brand name (Claude,
118
+ // Cursor, OpenCode…) so it doesn't read as a bare lowercase slug; else
119
+ // the slug itself.
120
+ name: hit?.name || CLI_DISPLAY_NAMES[String(slug).toLowerCase()] || slug,
121
+ emoji: hit?.emoji || null,
122
+ icon: hit?.icon || null,
123
+ };
124
+ };
125
+
126
+ /**
127
+ * Add `participant_faces` and a display `title` to an a2a / group thread.
128
+ *
129
+ * Anything without participants (a Telegram day, a web thread) is returned
130
+ * untouched — this decorates multi-agent threads, it does not reshape the
131
+ * ledger.
132
+ *
133
+ * A title the STORE derived from slugs (`andy~claude-code`'s pair join, or a
134
+ * group with no name of its own) is the same question asked before the faces
135
+ * were known, so it is answered again with them: "Andy · Claude". A group
136
+ * someone actually named keeps that name.
137
+ */
138
+ const decorate = (thread, localAgents = []) => {
139
+ const participants = Array.isArray(thread?.participants) ? thread.participants : null;
140
+ if (!participants?.length) return thread;
141
+ const faces = participants.map((slug) => face(slug, localAgents));
142
+ const own = String(thread.title || "");
143
+ const isDerived = !own || own === participants.join(" · ") || own === thread.id;
144
+ return {
145
+ ...thread,
146
+ participant_faces: faces,
147
+ title: isDerived ? faces.map((f) => f.name).join(" · ") : own,
148
+ };
149
+ };
150
+
151
+ return { face, decorate };
152
+ }
153
+
154
+ /** The same resolver, built from a ProjectManager-style list of entries. */
155
+ export function faceResolverFor(projects) {
156
+ let paths = [];
157
+ try { paths = projects.list().map((e) => e.path).filter(Boolean); } catch { /* none registered */ }
158
+ return createFaceResolver(paths);
159
+ }
@@ -10,7 +10,7 @@
10
10
  // POST /mcp/run call an MCP tool
11
11
  import fs from "node:fs";
12
12
  import path from "node:path";
13
- import { resolveMemoryPath } from "./shared.js";
13
+ import { resolveMemoryPath, asyncRoute } from "./shared.js";
14
14
 
15
15
  export function register(api, { projects, registries, resolveTopProject }) {
16
16
  // ---- /memory ----
@@ -117,7 +117,7 @@ export function register(api, { projects, registries, resolveTopProject }) {
117
117
  res.json(registries.for(p).list());
118
118
  });
119
119
 
120
- api.post("/mcp/run", async (req, res) => {
120
+ api.post("/mcp/run", asyncRoute(async (req, res) => {
121
121
  const { project: projectRef, name, tool, params } = req.body || {};
122
122
  if (!name) return res.status(400).json({ error: "name required" });
123
123
  if (!tool) return res.status(400).json({ error: "tool required" });
@@ -129,5 +129,5 @@ export function register(api, { projects, registries, resolveTopProject }) {
129
129
  } catch (e) {
130
130
  res.status(500).json({ error: e.message });
131
131
  }
132
- });
132
+ }));
133
133
  }
@@ -1,3 +1,4 @@
1
+ import { asyncRoute } from "./shared.js";
1
2
  // POST /transcribe/chunk
2
3
  // Raw audio bytes in the body. Headers:
3
4
  // X-Audio-Format webm | ogg | wav | mp3 (defaults to webm)
@@ -10,7 +11,7 @@ export function register(api) {
10
11
  // admin (mirror of /tts/providers). local = embedded faster-whisper;
11
12
  // openai = cloud Whisper; custom = any OpenAI-compatible server (mlx-audio
12
13
  // on Metal, a Radeon/NVIDIA box on the LAN, a remote endpoint).
13
- api.get("/transcribe/providers", async (_req, res) => {
14
+ api.get("/transcribe/providers", asyncRoute(async (_req, res) => {
14
15
  try {
15
16
  const { readConfig } = await import("#core/config/index.js");
16
17
  const { listSttProviders } = await import("#core/voice/transcription.js");
@@ -18,12 +19,12 @@ export function register(api) {
18
19
  } catch (e) {
19
20
  res.status(500).json({ error: e.message });
20
21
  }
21
- });
22
+ }));
22
23
 
23
24
  // GET /transcribe/hardware — detected machine + the recommended local backend
24
25
  // (mlx on Apple Silicon, faster-whisper cuda on NVIDIA, else CPU). Drives the
25
26
  // "engine adapts itself" UX in the web admin.
26
- api.get("/transcribe/hardware", async (_req, res) => {
27
+ api.get("/transcribe/hardware", asyncRoute(async (_req, res) => {
27
28
  try {
28
29
  const { detectHardware, recommendStt } = await import("#core/voice/stt-hardware.js");
29
30
  const hw = detectHardware();
@@ -31,11 +32,11 @@ export function register(api) {
31
32
  } catch (e) {
32
33
  res.status(500).json({ error: e.message });
33
34
  }
34
- });
35
+ }));
35
36
 
36
37
  // GET /transcribe/models?backend=faster|mlx — model catalog with on-disk
37
38
  // status (downloaded? size) for the model-manager UI.
38
- api.get("/transcribe/models", async (req, res) => {
39
+ api.get("/transcribe/models", asyncRoute(async (req, res) => {
39
40
  try {
40
41
  const backend = String(req.query.backend || "faster");
41
42
  const { listSttModels } = await import("#core/voice/stt-models.js");
@@ -43,21 +44,21 @@ export function register(api) {
43
44
  } catch (e) {
44
45
  res.status(500).json({ error: e.message });
45
46
  }
46
- });
47
+ }));
47
48
 
48
49
  // GET /transcribe/warmup — load the local whisper model (if needed) and reset
49
50
  // its idle watchdog. Callers (e.g. the desktop window) ping this while open so
50
51
  // the first real utterance doesn't pay the cold-load cost.
51
- api.get("/transcribe/warmup", async (_req, res) => {
52
+ api.get("/transcribe/warmup", asyncRoute(async (_req, res) => {
52
53
  try {
53
54
  const { warmupWhisper } = await import("../whisper-server.js");
54
55
  res.json(await warmupWhisper());
55
56
  } catch (e) {
56
57
  res.status(500).json({ ok: false, error: e.message });
57
58
  }
58
- });
59
+ }));
59
60
 
60
- api.post("/transcribe/chunk", async (req, res) => {
61
+ api.post("/transcribe/chunk", asyncRoute(async (req, res) => {
61
62
  const chunks = [];
62
63
  req.on("data", (c) => chunks.push(c));
63
64
  req.on("end", async () => {
@@ -86,5 +87,5 @@ export function register(api) {
86
87
  req.on("error", (e) =>
87
88
  res.status(500).json({ ok: false, error: e.message })
88
89
  );
89
- });
90
+ }));
90
91
  }