@maudecode/talaria-web 1.20.0 → 1.22.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (410) hide show
  1. package/_release.json +8 -8
  2. package/dist/api/automation-router.d.ts +319 -14
  3. package/dist/api/automation-router.js +21 -1
  4. package/dist/api/automation-router.js.map +1 -1
  5. package/dist/api/chat-router.d.ts +615 -69
  6. package/dist/api/chat-router.js +22 -170
  7. package/dist/api/chat-router.js.map +1 -1
  8. package/dist/api/git-router.d.ts +50 -0
  9. package/dist/api/git-router.js +17 -4
  10. package/dist/api/git-router.js.map +1 -1
  11. package/dist/api/groups-router.d.ts +764 -0
  12. package/dist/api/groups-router.js +79 -0
  13. package/dist/api/groups-router.js.map +1 -0
  14. package/dist/api/raw-routes.js +3 -1
  15. package/dist/api/raw-routes.js.map +1 -1
  16. package/dist/api/router.d.ts +1 -1
  17. package/dist/api/sessions-router.d.ts +1675 -167
  18. package/dist/api/sessions-router.js +67 -53
  19. package/dist/api/sessions-router.js.map +1 -1
  20. package/dist/api/settings-router.d.ts +911 -1
  21. package/dist/api/settings-router.js +53 -2
  22. package/dist/api/settings-router.js.map +1 -1
  23. package/dist/api/sse-routes.d.ts +1 -1
  24. package/dist/api/sse-routes.js +15 -5
  25. package/dist/api/sse-routes.js.map +1 -1
  26. package/dist/api/tools-raw.js +27 -136
  27. package/dist/api/tools-raw.js.map +1 -1
  28. package/dist/api/tools-router.d.ts +588 -51
  29. package/dist/api/tools-router.js +98 -16
  30. package/dist/api/tools-router.js.map +1 -1
  31. package/dist/app.js +5 -1
  32. package/dist/app.js.map +1 -1
  33. package/dist/auth/gate.js +5 -1
  34. package/dist/auth/gate.js.map +1 -1
  35. package/dist/config/agent-config.d.ts +6 -1
  36. package/dist/config/agent-config.js +75 -3
  37. package/dist/config/agent-config.js.map +1 -1
  38. package/dist/feedback.d.ts +18 -0
  39. package/dist/feedback.js +145 -0
  40. package/dist/feedback.js.map +1 -0
  41. package/dist/fs/stat.d.ts +2 -0
  42. package/dist/fs/stat.js +4 -0
  43. package/dist/fs/stat.js.map +1 -1
  44. package/dist/http/context.d.ts +9 -0
  45. package/dist/http/context.js +0 -6
  46. package/dist/http/context.js.map +1 -1
  47. package/dist/http/pinned.js +19 -8
  48. package/dist/http/pinned.js.map +1 -1
  49. package/dist/providers/catalog.d.ts +9 -1
  50. package/dist/providers/catalog.js +86 -6
  51. package/dist/providers/catalog.js.map +1 -1
  52. package/dist/redact.d.ts +2 -0
  53. package/dist/redact.js +26 -5
  54. package/dist/redact.js.map +1 -1
  55. package/dist/runtime.js +62 -11
  56. package/dist/runtime.js.map +1 -1
  57. package/dist/server.js +2 -0
  58. package/dist/server.js.map +1 -1
  59. package/dist/sessions/admission.d.ts +21 -0
  60. package/dist/sessions/admission.js +176 -0
  61. package/dist/sessions/admission.js.map +1 -0
  62. package/dist/sessions/anchor.d.ts +5 -2
  63. package/dist/sessions/anchor.js +14 -13
  64. package/dist/sessions/anchor.js.map +1 -1
  65. package/dist/sessions/background-tasks.d.ts +19 -1
  66. package/dist/sessions/background-tasks.js +36 -6
  67. package/dist/sessions/background-tasks.js.map +1 -1
  68. package/dist/sessions/cli-sessions.js +11 -6
  69. package/dist/sessions/cli-sessions.js.map +1 -1
  70. package/dist/sessions/compress.d.ts +10 -9
  71. package/dist/sessions/compress.js +31 -20
  72. package/dist/sessions/compress.js.map +1 -1
  73. package/dist/sessions/events.d.ts +3 -0
  74. package/dist/sessions/events.js +4 -0
  75. package/dist/sessions/events.js.map +1 -1
  76. package/dist/sessions/gateway-sessions.d.ts +61 -2
  77. package/dist/sessions/gateway-sessions.js +223 -35
  78. package/dist/sessions/gateway-sessions.js.map +1 -1
  79. package/dist/sessions/gateway-watcher.js +8 -4
  80. package/dist/sessions/gateway-watcher.js.map +1 -1
  81. package/dist/sessions/groups.d.ts +60 -0
  82. package/dist/sessions/groups.js +339 -0
  83. package/dist/sessions/groups.js.map +1 -0
  84. package/dist/sessions/list.d.ts +7 -2
  85. package/dist/sessions/list.js +13 -4
  86. package/dist/sessions/list.js.map +1 -1
  87. package/dist/sessions/merge.d.ts +15 -5
  88. package/dist/sessions/merge.js +49 -15
  89. package/dist/sessions/merge.js.map +1 -1
  90. package/dist/sessions/pending.d.ts +1 -1
  91. package/dist/sessions/pending.js +15 -6
  92. package/dist/sessions/pending.js.map +1 -1
  93. package/dist/sessions/prefix-index.d.ts +9 -14
  94. package/dist/sessions/prefix-index.js +14 -52
  95. package/dist/sessions/prefix-index.js.map +1 -1
  96. package/dist/sessions/prompt-queues.d.ts +36 -0
  97. package/dist/sessions/prompt-queues.js +318 -0
  98. package/dist/sessions/prompt-queues.js.map +1 -0
  99. package/dist/sessions/reasoning-display.d.ts +2 -0
  100. package/dist/sessions/reasoning-display.js +31 -0
  101. package/dist/sessions/reasoning-display.js.map +1 -0
  102. package/dist/sessions/relay.d.ts +16 -2
  103. package/dist/sessions/relay.js +119 -24
  104. package/dist/sessions/relay.js.map +1 -1
  105. package/dist/sessions/service.d.ts +33 -3
  106. package/dist/sessions/service.js +304 -70
  107. package/dist/sessions/service.js.map +1 -1
  108. package/dist/sessions/session.d.ts +6 -0
  109. package/dist/sessions/session.js +14 -0
  110. package/dist/sessions/session.js.map +1 -1
  111. package/dist/sessions/shares.d.ts +1 -1
  112. package/dist/sessions/shares.js +13 -4
  113. package/dist/sessions/shares.js.map +1 -1
  114. package/dist/sessions/state-db.d.ts +2 -1
  115. package/dist/sessions/state-db.js +7 -3
  116. package/dist/sessions/state-db.js.map +1 -1
  117. package/dist/sessions/storage/json-documents.js +3 -0
  118. package/dist/sessions/storage/json-documents.js.map +1 -1
  119. package/dist/sessions/store.d.ts +2 -0
  120. package/dist/sessions/store.js +11 -3
  121. package/dist/sessions/store.js.map +1 -1
  122. package/dist/sessions/streams.d.ts +4 -0
  123. package/dist/sessions/streams.js +12 -0
  124. package/dist/sessions/streams.js.map +1 -1
  125. package/dist/sessions/todo.js +10 -1
  126. package/dist/sessions/todo.js.map +1 -1
  127. package/dist/sessions/tool-display.d.ts +8 -1
  128. package/dist/sessions/tool-display.js +39 -4
  129. package/dist/sessions/tool-display.js.map +1 -1
  130. package/dist/sessions/turn.d.ts +4 -1
  131. package/dist/sessions/turn.js +53 -22
  132. package/dist/sessions/turn.js.map +1 -1
  133. package/dist/settings.js +2 -1
  134. package/dist/settings.js.map +1 -1
  135. package/dist/spa.js +1 -1
  136. package/dist/spa.js.map +1 -1
  137. package/dist/test/group-fixture.d.ts +66 -0
  138. package/dist/test/group-fixture.js +89 -0
  139. package/dist/test/group-fixture.js.map +1 -0
  140. package/dist/test/harness.d.ts +3 -0
  141. package/dist/test/harness.js +3 -0
  142. package/dist/test/harness.js.map +1 -1
  143. package/dist/tools/connectors.d.ts +9 -1
  144. package/dist/tools/connectors.js +48 -0
  145. package/dist/tools/connectors.js.map +1 -1
  146. package/dist/tools/kanban.d.ts +10 -1
  147. package/dist/tools/kanban.js +73 -1
  148. package/dist/tools/kanban.js.map +1 -1
  149. package/dist/tools/mcp.d.ts +3 -1
  150. package/dist/tools/mcp.js +73 -0
  151. package/dist/tools/mcp.js.map +1 -1
  152. package/dist/tools/memory.d.ts +28 -0
  153. package/dist/tools/memory.js +120 -14
  154. package/dist/tools/memory.js.map +1 -1
  155. package/dist/tools/skills.d.ts +6 -0
  156. package/dist/tools/skills.js +17 -0
  157. package/dist/tools/skills.js.map +1 -1
  158. package/dist/tools/update-notifications.d.ts +12 -10
  159. package/dist/tools/update-notifications.js +124 -14
  160. package/dist/tools/update-notifications.js.map +1 -1
  161. package/dist/tools/updates.d.ts +38 -12
  162. package/dist/tools/updates.js +180 -44
  163. package/dist/tools/updates.js.map +1 -1
  164. package/dist/workspace/fs.d.ts +2 -0
  165. package/dist/workspace/fs.js +63 -1
  166. package/dist/workspace/fs.js.map +1 -1
  167. package/dist/workspace/managed-buffers.d.ts +58 -0
  168. package/dist/workspace/managed-buffers.js +76 -0
  169. package/dist/workspace/managed-buffers.js.map +1 -0
  170. package/dist/workspace/rollback.js +1 -1
  171. package/dist/workspace/rollback.js.map +1 -1
  172. package/dist/workspace/upload.d.ts +1 -1
  173. package/dist/workspace/upload.js +52 -37
  174. package/dist/workspace/upload.js.map +1 -1
  175. package/dist/workspace/workspaces.d.ts +5 -1
  176. package/dist/workspace/workspaces.js +32 -6
  177. package/dist/workspace/workspaces.js.map +1 -1
  178. package/package.json +2 -2
  179. package/sidecar/agent_dependency.json +4 -4
  180. package/sidecar/agent_importer.json +8 -0
  181. package/sidecar/agent_support.json +20 -8
  182. package/sidecar/scripts/agent_importer_contract.py +19 -0
  183. package/sidecar/scripts/test.sh +3 -1
  184. package/sidecar/talaria_sidecar/__init__.py +1 -1
  185. package/sidecar/talaria_sidecar/agent_mutation.py +87 -9
  186. package/sidecar/talaria_sidecar/agent_services.py +83 -23
  187. package/sidecar/talaria_sidecar/home.py +12 -5
  188. package/sidecar/talaria_sidecar/methods/__init__.py +2 -2
  189. package/sidecar/talaria_sidecar/methods/agent_imports.py +346 -0
  190. package/sidecar/talaria_sidecar/methods/chat.py +141 -58
  191. package/sidecar/talaria_sidecar/methods/commands.py +6 -4
  192. package/sidecar/talaria_sidecar/methods/config.py +8 -3
  193. package/sidecar/talaria_sidecar/methods/connectors.py +138 -4
  194. package/sidecar/talaria_sidecar/methods/dashboard_plugins.py +25 -4
  195. package/sidecar/talaria_sidecar/methods/delegation.py +126 -0
  196. package/sidecar/talaria_sidecar/methods/gateway.py +5 -0
  197. package/sidecar/talaria_sidecar/methods/gateway_sessions.py +142 -23
  198. package/sidecar/talaria_sidecar/methods/groups.py +120 -0
  199. package/sidecar/talaria_sidecar/methods/kanban.py +48 -0
  200. package/sidecar/talaria_sidecar/methods/managed_buffers.py +110 -0
  201. package/sidecar/talaria_sidecar/methods/mcp.py +55 -0
  202. package/sidecar/talaria_sidecar/methods/memory.py +27 -3
  203. package/sidecar/talaria_sidecar/methods/nous_account.py +130 -0
  204. package/sidecar/talaria_sidecar/methods/oauth.py +25 -4
  205. package/sidecar/talaria_sidecar/methods/outbound_drafts.py +147 -0
  206. package/sidecar/talaria_sidecar/methods/plugin_catalog.py +73 -2
  207. package/sidecar/talaria_sidecar/methods/providers.py +51 -1
  208. package/sidecar/talaria_sidecar/methods/skill_revisions.py +177 -0
  209. package/sidecar/talaria_sidecar/methods/skills.py +10 -0
  210. package/sidecar/talaria_sidecar/methods/tts.py +67 -0
  211. package/sidecar/talaria_sidecar/rpc.py +11 -2
  212. package/static/dist/FILES.txt +155 -144
  213. package/static/dist/THIRD_PARTY_LICENSES.md +1 -1
  214. package/static/dist/assets/AppShell-hvysbd9x.js +8 -0
  215. package/static/dist/assets/Button-dlsibkzq.js +1 -0
  216. package/static/dist/assets/ChatPage-jikwrwfd.js +2 -0
  217. package/static/dist/assets/Composer-mnke8ss2.js +5 -0
  218. package/static/dist/assets/ConnectTargets-ejplzo4q.js +1 -0
  219. package/static/dist/assets/Dialog-rksfyyq5.js +1 -0
  220. package/static/dist/assets/{ExtensionRoute-zrhjn0wm.js → ExtensionRoute-igk5h0rj.js} +1 -1
  221. package/static/dist/assets/HubRoute-eooassx4.js +2 -0
  222. package/static/dist/assets/Markdown-m5pzgvtx.js +2 -0
  223. package/static/dist/assets/{MarkdownRenderer-fbswsgld.js → MarkdownRenderer-74ysuomr.js} +18 -18
  224. package/static/dist/assets/OAuthSignIn-i4flsuq2.js +1 -0
  225. package/static/dist/assets/QueueCard-msz9wd1m.js +1 -0
  226. package/static/dist/assets/ResourceSwitch-b70zg4xd.js +1 -0
  227. package/static/dist/assets/RightPanel-f5v61m8j.js +1 -0
  228. package/static/dist/assets/Select-f3l897pt.js +1 -0
  229. package/static/dist/assets/SessionListPanel-brnzacw9.js +1 -0
  230. package/static/dist/assets/SettingsLayout-f4akmrt2.js +1 -0
  231. package/static/dist/assets/States-msohx3c0.js +1 -0
  232. package/static/dist/assets/TerminalPanel-bnu5xawo.js +16 -0
  233. package/static/dist/assets/Toaster-d6col3ch.js +1 -0
  234. package/static/dist/assets/_app-lrjgufcy.js +1 -0
  235. package/static/dist/assets/{_app.ext._extensionId-na62087t.js → _app.ext._extensionId-k3xitxr1.js} +1 -1
  236. package/static/dist/assets/_app.groups-bt4wdwnd.js +1 -0
  237. package/static/dist/assets/{_app.index-jypgdqoi.js → _app.index-n3otiki0.js} +1 -1
  238. package/static/dist/assets/{_app.insights-kabejdtm.js → _app.insights-b0mzlh6m.js} +1 -1
  239. package/static/dist/assets/{_app.kanban-m19kfcmx.js → _app.kanban-d923g7j5.js} +1 -1
  240. package/static/dist/assets/{_app.logs-iw4m96sz.js → _app.logs-donegue1.js} +1 -1
  241. package/static/dist/assets/{_app.memory-jq5frwcg.js → _app.memory-hdnled08.js} +1 -1
  242. package/static/dist/assets/{_app.profiles-kwa3m7rp.js → _app.profiles-fumot3jk.js} +1 -1
  243. package/static/dist/assets/{_app.session._sessionId-o5lyeipj.js → _app.session._sessionId-crmdl2ux.js} +1 -1
  244. package/static/dist/assets/{_app.settings-ckl8hdll.js → _app.settings-jui8iesz.js} +1 -1
  245. package/static/dist/assets/_app.settings._section-do84hsqw.js +3 -0
  246. package/static/dist/assets/{_app.skills-n016rihd.js → _app.skills-heqcn21m.js} +1 -1
  247. package/static/dist/assets/_app.tasks-jiudtutt.js +1 -0
  248. package/static/dist/assets/{_app.todos-btew5v2s.js → _app.todos-bl6kk2zq.js} +1 -1
  249. package/static/dist/assets/{_app.workspaces-lnfk95ch.js → _app.workspaces-frvh3o7w.js} +1 -1
  250. package/static/dist/assets/_delete-qnxuo87s.js +1 -0
  251. package/static/dist/assets/{abnfDiagram-VCTEODGH-dttheegb.js → abnfDiagram-VCTEODGH-dppg3yfx.js} +1 -1
  252. package/static/dist/assets/{architecture-7GRP2DOG-ic435919.js → architecture-7GRP2DOG-gbajejh3.js} +1 -1
  253. package/static/dist/assets/{architectureDiagram-5GKGNRK7-8r3glgiq.js → architectureDiagram-5GKGNRK7-bzrxyais.js} +1 -1
  254. package/static/dist/assets/archive-yhdyz231.js +1 -0
  255. package/static/dist/assets/autoReadClaim-nlyv8tu9.js +1 -0
  256. package/static/dist/assets/{blockDiagram-I7D4REHJ-jenyos6c.js → blockDiagram-I7D4REHJ-gmk9koab.js} +1 -1
  257. package/static/dist/assets/{c4Diagram-7LVT6UL2-nzlx7yc4.js → c4Diagram-7LVT6UL2-bfqiqqcz.js} +1 -1
  258. package/static/dist/assets/channel-grt3rob4.js +1 -0
  259. package/static/dist/assets/{chunk-4HAMMTFA-g0cru63b.js → chunk-4HAMMTFA-i9s6h4wv.js} +1 -1
  260. package/static/dist/assets/{chunk-75Z2AOVW-7rkswkjw.js → chunk-75Z2AOVW-gnt6pnso.js} +1 -1
  261. package/static/dist/assets/{chunk-DU6HZSFF-fn73jzdo.js → chunk-DU6HZSFF-gq439wot.js} +3 -3
  262. package/static/dist/assets/{chunk-F27PBJKO-oey8e72m.js → chunk-F27PBJKO-wvx90pbt.js} +1 -1
  263. package/static/dist/assets/{chunk-GMAD6QVW-l2a32wiy.js → chunk-GMAD6QVW-mc2gu30k.js} +1 -1
  264. package/static/dist/assets/{chunk-GVQU2GXP-o9dwzh8h.js → chunk-GVQU2GXP-f8fxa2ym.js} +1 -1
  265. package/static/dist/assets/{chunk-IMKFNOWR-eblwj20b.js → chunk-IMKFNOWR-lnsl31hj.js} +1 -1
  266. package/static/dist/assets/{chunk-L3NEJ4N5-o2mufspb.js → chunk-L3NEJ4N5-kbfdidwu.js} +1 -1
  267. package/static/dist/assets/{chunk-OSK3NFVY-ijp9pw29.js → chunk-OSK3NFVY-dvxsduj6.js} +1 -1
  268. package/static/dist/assets/{chunk-P2QGCYS3-hs9hqwl4.js → chunk-P2QGCYS3-ivo3i1wf.js} +1 -1
  269. package/static/dist/assets/{chunk-POPQ4Y6H-bp9rsqez.js → chunk-POPQ4Y6H-i0gfu0hx.js} +1 -1
  270. package/static/dist/assets/{chunk-PWAF6VOD-brkprov6.js → chunk-PWAF6VOD-jb0fdyb0.js} +1 -1
  271. package/static/dist/assets/{chunk-SHT3W25Y-gmpv0pxz.js → chunk-SHT3W25Y-b7ou2xsp.js} +1 -1
  272. package/static/dist/assets/{chunk-SVP7TREG-oldm08fu.js → chunk-SVP7TREG-e2v7me5v.js} +1 -1
  273. package/static/dist/assets/{chunk-TICWLB2K-ooqilfv7.js → chunk-TICWLB2K-e5zlai62.js} +1 -1
  274. package/static/dist/assets/classDiagram-ZZMXUADV-nnsp49jr.js +1 -0
  275. package/static/dist/assets/classDiagram-v2-VYDZK3BY-nnsp49jr.js +1 -0
  276. package/static/dist/assets/completionAudio-c5at041z.js +1 -0
  277. package/static/dist/assets/{copy-jo006coq.js → copy-jj3oiw13.js} +1 -1
  278. package/static/dist/assets/{cynefin-OW5HDTMX-d47op7qs.js → cynefin-OW5HDTMX-n5n1ck70.js} +1 -1
  279. package/static/dist/assets/{cynefinDiagram-5FMLGOSQ-doa7594y.js → cynefinDiagram-5FMLGOSQ-b33npu4f.js} +1 -1
  280. package/static/dist/assets/{dagre-GXQ25YYZ-os768dp4.js → dagre-GXQ25YYZ-miwvae07.js} +1 -1
  281. package/static/dist/assets/{diagram-S7CK7UJ4-fyi81nxd.js → diagram-S7CK7UJ4-j8fphsp4.js} +1 -1
  282. package/static/dist/assets/{diagram-UQ7AKVKN-j3exggaq.js → diagram-UQ7AKVKN-5cixo166.js} +1 -1
  283. package/static/dist/assets/{diagram-VSXAHHWV-omo1en2l.js → diagram-VSXAHHWV-ii3bf92m.js} +1 -1
  284. package/static/dist/assets/{diagram-VX7I27RA-oro2cyu0.js → diagram-VX7I27RA-b3cfgx81.js} +1 -1
  285. package/static/dist/assets/{diagram-Z3DM3KII-byt9vdb7.js → diagram-Z3DM3KII-bey9lqr8.js} +1 -1
  286. package/static/dist/assets/{dist-etpoyscq.js → dist-cb8um5dh.js} +4 -4
  287. package/static/dist/assets/{dist-crc46di9.js → dist-kpg5ccm9.js} +1 -1
  288. package/static/dist/assets/{ebnfDiagram-PWID7BFC-ee3haugh.js → ebnfDiagram-PWID7BFC-2m4wrnqc.js} +1 -1
  289. package/static/dist/assets/{erDiagram-RLTQ6QDP-d1e93yff.js → erDiagram-RLTQ6QDP-kak5te0n.js} +1 -1
  290. package/static/dist/assets/{eventmodeling-NTZA5JFV-i1ihb40c.js → eventmodeling-NTZA5JFV-ojcc486t.js} +1 -1
  291. package/static/dist/assets/flowDiagram-HODETNUW-kxr9sicu.js +1 -0
  292. package/static/dist/assets/folder-plus-fk6j7tlv.js +1 -0
  293. package/static/dist/assets/{ganttDiagram-EL5Y4UJY-m7g0jud4.js → ganttDiagram-EL5Y4UJY-k6nfmhrh.js} +1 -1
  294. package/static/dist/assets/getPseudoElementBounds-mwj3vqni.js +1 -0
  295. package/static/dist/assets/{gitGraph-4MIJSDKK-hzdj07yy.js → gitGraph-4MIJSDKK-bxq1lbhy.js} +1 -1
  296. package/static/dist/assets/{gitGraphDiagram-WWUBYQGX-dm9agbna.js → gitGraphDiagram-WWUBYQGX-ehvoankt.js} +1 -1
  297. package/static/dist/assets/group_discussions-fk5hry4l.js +1 -0
  298. package/static/dist/assets/{highlighted-body-KPVGNVTW-mmgz2czu.js → highlighted-body-KPVGNVTW-nr4nfdq7.js} +1 -1
  299. package/static/dist/assets/{host-fr6lni1p.js → host-dhgqiozp.js} +1 -1
  300. package/static/dist/assets/index-hx7z4wdj.js +13 -0
  301. package/static/dist/assets/index-o8ebuc5x.css +2 -0
  302. package/static/dist/assets/{info-A6RAGUB7-lll1dqmm.js → info-A6RAGUB7-dtsj0ybw.js} +1 -1
  303. package/static/dist/assets/{infoDiagram-27XIBGKW-k7esc639.js → infoDiagram-27XIBGKW-jena90ao.js} +1 -1
  304. package/static/dist/assets/{ishikawaDiagram-5VMMS53U-lgr6k9wo.js → ishikawaDiagram-5VMMS53U-kia6bn5u.js} +1 -1
  305. package/static/dist/assets/{journeyDiagram-3NMN7TZE-ndmbxuqk.js → journeyDiagram-3NMN7TZE-ipsa6icb.js} +1 -1
  306. package/static/dist/assets/{kanban-definition-UXKFOSKX-mjxym0jp.js → kanban-definition-UXKFOSKX-moxx59kp.js} +1 -1
  307. package/static/dist/assets/katex-ic33v820.js +257 -0
  308. package/static/dist/assets/katex-qcv7xo0t.css +1 -0
  309. package/static/dist/assets/{lazyRouteComponent-cwb6l7xh.js → lazyRouteComponent-i74ujrfk.js} +1 -1
  310. package/static/dist/assets/{line-mtr5k6il.js → line-lgrkg9no.js} +1 -1
  311. package/static/dist/assets/link-2-fp49mwl2.js +1 -0
  312. package/static/dist/assets/{link-iadw4ghw.js → link-es18mse1.js} +2 -2
  313. package/static/dist/assets/{locale-cs-n41hptse.js → locale-cs-brltdkcp.js} +1 -1
  314. package/static/dist/assets/{locale-de-k7ht47ew.js → locale-de-h6e9oq6v.js} +1 -1
  315. package/static/dist/assets/{locale-es-ih078lco.js → locale-es-oklmh80f.js} +1 -1
  316. package/static/dist/assets/{locale-fr-ojabnf41.js → locale-fr-b17ozoi2.js} +1 -1
  317. package/static/dist/assets/{locale-it-kb96jufy.js → locale-it-whe01eef.js} +1 -1
  318. package/static/dist/assets/{locale-ja-jpsp3xs1.js → locale-ja-g1s0rtpc.js} +1 -1
  319. package/static/dist/assets/{locale-pl-dbap4leu.js → locale-pl-d9p3lqcb.js} +1 -1
  320. package/static/dist/assets/{locale-pt-nci7w72x.js → locale-pt-l75on74f.js} +1 -1
  321. package/static/dist/assets/{locale-ru-soghe4cs.js → locale-ru-wl3mbsaw.js} +1 -1
  322. package/static/dist/assets/{locale-tr-ks00mu68.js → locale-tr-cz87itrq.js} +1 -1
  323. package/static/dist/assets/{locale-vi-ij7twfm6.js → locale-vi-elqj1y4k.js} +1 -1
  324. package/static/dist/assets/{locale-zh-Hant-feakwr7a.js → locale-zh-Hant-hf8gqm7d.js} +1 -1
  325. package/static/dist/assets/{locale-zh-ren0vjyv.js → locale-zh-cdckwb0u.js} +1 -1
  326. package/static/dist/assets/login-o6gfl4gy.js +1 -0
  327. package/static/dist/assets/mermaid-HWGCJPDP-n2kbzsao.js +1 -0
  328. package/static/dist/assets/{mermaid-parser.core-k91vdnvi.js → mermaid-parser.core-fflovwf2.js} +3 -3
  329. package/static/dist/assets/{mindmap-definition-YA3MSWOX-ehztfea4.js → mindmap-definition-YA3MSWOX-ic8l9whi.js} +1 -1
  330. package/static/dist/assets/onboarding-bxm7gdrr.js +1 -0
  331. package/static/dist/assets/{packet-AYTQ26CC-ok2xrblz.js → packet-AYTQ26CC-ntci3088.js} +1 -1
  332. package/static/dist/assets/{pegDiagram-XKGWAZYB-ec3rpj0m.js → pegDiagram-XKGWAZYB-e3btz04w.js} +1 -1
  333. package/static/dist/assets/{pie-WAS4IAKB-iwkir23u.js → pie-WAS4IAKB-o2dc7l36.js} +1 -1
  334. package/static/dist/assets/{pieDiagram-E7YTZNPT-fcpqpekh.js → pieDiagram-E7YTZNPT-gro55rrw.js} +1 -1
  335. package/static/dist/assets/presence-lq6m12ga.js +1 -0
  336. package/static/dist/assets/prompt_queue_cancelled-cebcuagu.js +1 -0
  337. package/static/dist/assets/{quadrantDiagram-AXDQQJYC-lqsync43.js → quadrantDiagram-AXDQQJYC-fxulmd7d.js} +1 -1
  338. package/static/dist/assets/queryKeys-cnvn6pea.js +9 -0
  339. package/static/dist/assets/{radar-RG4KPBEZ-hje4jbk6.js → radar-RG4KPBEZ-9pcospra.js} +1 -1
  340. package/static/dist/assets/{railroad-74A4TZTK-gll9n6qi.js → railroad-74A4TZTK-nzdga12j.js} +1 -1
  341. package/static/dist/assets/{railroad-abnf-HS5TGJTU-o6h6lpn4.js → railroad-abnf-HS5TGJTU-ep3ytel0.js} +1 -1
  342. package/static/dist/assets/{railroad-ebnf-LZEXJU2U-juaefj6o.js → railroad-ebnf-LZEXJU2U-iw7uc1wy.js} +1 -1
  343. package/static/dist/assets/{railroad-peg-WCYAUIDC-cgfhvpah.js → railroad-peg-WCYAUIDC-fo3b3gme.js} +1 -1
  344. package/static/dist/assets/{railroadDiagram-O6MQD6OU-lp3w7awf.js → railroadDiagram-O6MQD6OU-lxpxf8f0.js} +1 -1
  345. package/static/dist/assets/{refresh-cw-iccm7a4e.js → refresh-cw-d14h79x5.js} +1 -1
  346. package/static/dist/assets/rename-ccd52yws.js +1 -0
  347. package/static/dist/assets/{requirementDiagram-BXWQKSXE-ha8eibcf.js → requirementDiagram-BXWQKSXE-lrozucd2.js} +1 -1
  348. package/static/dist/assets/{sankeyDiagram-P5KCCOFB-oxf31pr9.js → sankeyDiagram-P5KCCOFB-iusxy9mq.js} +1 -1
  349. package/static/dist/assets/{sequenceDiagram-WJ2MYXX4-jiq8lhyo.js → sequenceDiagram-WJ2MYXX4-o987q8ti.js} +1 -1
  350. package/static/dist/assets/{share._token-o76ki0ly.js → share._token-bfw7f9m5.js} +1 -1
  351. package/static/dist/assets/sliders-horizontal-l65hoa3x.js +1 -0
  352. package/static/dist/assets/{stateDiagram-D77RDMKH-f3fslnon.js → stateDiagram-D77RDMKH-hh23v7y5.js} +1 -1
  353. package/static/dist/assets/stateDiagram-v2-MP3YSRHH-jukr0d8h.js +1 -0
  354. package/static/dist/assets/{swimlanes-42K2YHIH-k1hmk7jf.js → swimlanes-42K2YHIH-gj2t3rm8.js} +1 -1
  355. package/static/dist/assets/swimlanesDiagram-VR7AAH4N-ik9m9j2m.js +8 -0
  356. package/static/dist/assets/{timeline-definition-24CTP7MA-n3ncfy9r.js → timeline-definition-24CTP7MA-84s2w2sr.js} +1 -1
  357. package/static/dist/assets/toast-gqqcvxiy.js +56 -0
  358. package/static/dist/assets/{treeView-Q6P3EWNA-l3y2pejt.js → treeView-Q6P3EWNA-cmuj50l7.js} +1 -1
  359. package/static/dist/assets/{treemap-WGGIJYW6-jown9axh.js → treemap-WGGIJYW6-dpjlg0xc.js} +1 -1
  360. package/static/dist/assets/tts-jw84jlqy.js +1 -0
  361. package/static/dist/assets/{useForm-o4uu74mx.js → useForm-lxzhiqao.js} +1 -1
  362. package/static/dist/assets/{useParams-ftsveu84.js → useParams-dt6gkoq7.js} +1 -1
  363. package/static/dist/assets/{useSearch-crqueqga.js → useSearch-o8t49csk.js} +1 -1
  364. package/static/dist/assets/useTranscript-gx9umcc2.js +1 -0
  365. package/static/dist/assets/{vennDiagram-4TSXK5OY-dh59uq1c.js → vennDiagram-4TSXK5OY-g9g5o8vy.js} +1 -1
  366. package/static/dist/assets/{wardley-WFR3VGLG-e6d74b0j.js → wardley-WFR3VGLG-ij35obrl.js} +1 -1
  367. package/static/dist/assets/{wardleyDiagram-VM6X3IG4-hnofh78f.js → wardleyDiagram-VM6X3IG4-f9my7q7w.js} +1 -1
  368. package/static/dist/assets/{xychartDiagram-S5SC5T6Z-bpymjelb.js → xychartDiagram-S5SC5T6Z-olqx1s1p.js} +1 -1
  369. package/static/dist/index.html +1 -1
  370. package/static/dist/sw.js +1 -1
  371. package/static/dist/assets/AppShell-3isgvoro.js +0 -8
  372. package/static/dist/assets/Button-f4n6dapf.js +0 -1
  373. package/static/dist/assets/ChatPage-k7b6xfax.js +0 -4
  374. package/static/dist/assets/ConnectTargets-juqvt5lm.js +0 -1
  375. package/static/dist/assets/Dialog-hta5utr3.js +0 -1
  376. package/static/dist/assets/Field-b6ez48oz.js +0 -1
  377. package/static/dist/assets/HubRoute-iwvso2tz.js +0 -2
  378. package/static/dist/assets/Markdown-jdeth7zq.js +0 -2
  379. package/static/dist/assets/OAuthSignIn-bpd8hom3.js +0 -1
  380. package/static/dist/assets/ResourceSwitch-odi6dy2o.js +0 -1
  381. package/static/dist/assets/RightPanel-eu6enlo6.js +0 -1
  382. package/static/dist/assets/Select-kr07928w.js +0 -1
  383. package/static/dist/assets/SessionListPanel-etb2i54l.js +0 -1
  384. package/static/dist/assets/SettingsLayout-eu3xxp23.js +0 -1
  385. package/static/dist/assets/States-icab19yg.js +0 -1
  386. package/static/dist/assets/TerminalPanel-hngmsr8b.js +0 -16
  387. package/static/dist/assets/Toaster-nb2uzjw1.js +0 -1
  388. package/static/dist/assets/_app-ga1moszl.js +0 -1
  389. package/static/dist/assets/_app.settings._section-dtdjk98a.js +0 -3
  390. package/static/dist/assets/_app.tasks-n8zuqsqe.js +0 -1
  391. package/static/dist/assets/archive-il7c6053.js +0 -1
  392. package/static/dist/assets/cancel-bsnfo36u.js +0 -1
  393. package/static/dist/assets/channel-dsbtk01y.js +0 -1
  394. package/static/dist/assets/classDiagram-ZZMXUADV-fvgcv24g.js +0 -1
  395. package/static/dist/assets/classDiagram-v2-VYDZK3BY-fvgcv24g.js +0 -1
  396. package/static/dist/assets/flowDiagram-HODETNUW-jahfpiod.js +0 -1
  397. package/static/dist/assets/folder-plus-ivoglq98.js +0 -1
  398. package/static/dist/assets/index-73649w7o.js +0 -10
  399. package/static/dist/assets/index-lhf1fsdf.css +0 -2
  400. package/static/dist/assets/katex-cbdd1ohw.css +0 -1
  401. package/static/dist/assets/katex-pbij2oo6.js +0 -257
  402. package/static/dist/assets/login-lkhtzfcl.js +0 -1
  403. package/static/dist/assets/mermaid-HWGCJPDP-jx0q5dm2.js +0 -1
  404. package/static/dist/assets/onboarding-f67z0a2r.js +0 -1
  405. package/static/dist/assets/queryKeys-ed4n2egc.js +0 -9
  406. package/static/dist/assets/refresh-i9ya9dvl.js +0 -1
  407. package/static/dist/assets/sliders-horizontal-ddcs88av.js +0 -1
  408. package/static/dist/assets/stateDiagram-v2-MP3YSRHH-hlt6yphw.js +0 -1
  409. package/static/dist/assets/swimlanesDiagram-VR7AAH4N-hd5t9tnt.js +0 -8
  410. package/static/dist/assets/toast-liparz2j.js +0 -56
@@ -228,6 +228,18 @@ def _unavailable_plugin(provider_id: str) -> bool:
228
228
  return not any(p is profile for _name, p in installed_plugin_profiles())
229
229
 
230
230
 
231
+ def require_runtime_ownership(requested: str | None) -> None:
232
+ """A process-wide Agent registry must not lend another home's plugin to this runtime."""
233
+ if not requested:
234
+ return
235
+ try:
236
+ if not _unavailable_plugin(requested.strip().lower()):
237
+ return
238
+ except Exception: # noqa: BLE001 - an unverified plugin owner cannot authorize execution
239
+ log.debug("runtime plugin ownership check failed", exc_info=True)
240
+ raise RpcError("Requested provider is unavailable in this profile", condition="credential_missing")
241
+
242
+
231
243
  def _agent_knows_provider(name: str) -> bool:
232
244
  """Whether the Agent's auth layer can resolve this provider id at all.
233
245
 
@@ -323,6 +335,35 @@ def model_ids(provider_id: str, *, force_refresh: bool) -> tuple[list[str], bool
323
335
  return [], False
324
336
 
325
337
 
338
+ def model_allowance_snapshot(provider_id: str, *, force_refresh: bool) -> dict:
339
+ """Native picker metadata in this call's scoped home; no billing write or second usage poll."""
340
+ if provider_id != "nous":
341
+ return {}
342
+ try:
343
+ from hermes_cli.inventory import build_model_options_payload, load_picker_context
344
+ from hermes_cli.model_picker_usage import nous_picker_usage
345
+ except ImportError:
346
+ return {"metadata_status": "unsupported"}
347
+ try:
348
+ payload = build_model_options_payload(load_picker_context(), refresh=force_refresh)
349
+ row = next((r for r in payload.get("providers", []) if r.get("slug") == provider_id), {})
350
+ pending = row.get("pricing_pending") is True or row.get("free_tier_pending") is True
351
+ plan = row.get("plan_usage")
352
+ fresh = nous_picker_usage() if isinstance(plan, dict) else None
353
+ return {
354
+ "metadata_status": "pending" if pending else "stale" if plan and fresh is None else "current",
355
+ "plan_usage": plan if isinstance(plan, dict) else None,
356
+ "usage_levels": {mid: level for mid, level in (row.get("usage_levels") or {}).items()
357
+ if isinstance(mid, str) and level in ("free", "low", "medium", "top_tier")},
358
+ "unavailable_model_ids": [mid for mid in row.get("unavailable_models", []) if isinstance(mid, str)] if not pending else [],
359
+ "allowance_pending": pending,
360
+ "free_tier": row.get("free_tier") if isinstance(row.get("free_tier"), bool) else None,
361
+ }
362
+ except Exception: # noqa: BLE001 - unknown entitlement is not unavailability
363
+ log.debug("native picker allowance unavailable", exc_info=True)
364
+ return {"metadata_status": "error"}
365
+
366
+
326
367
  def _requests_local_runtime(requested: str | None) -> bool:
327
368
  """Whether a resolution asks for the Agent's managed llama.cpp provider, picked the way the Agent picks it: the
328
369
  named provider, else the profile's, else ``HERMES_INFERENCE_PROVIDER``."""
@@ -367,6 +408,7 @@ def local_models() -> dict:
367
408
 
368
409
 
369
410
  def resolve_runtime(*, requested: str | None, api_key: str | None, base_url: str | None, target_model: str | None) -> dict:
411
+ require_runtime_ownership(requested)
370
412
  try:
371
413
  from hermes_cli.runtime_provider import format_runtime_provider_error, resolve_runtime_provider
372
414
  except Exception as exc: # noqa: BLE001
@@ -535,6 +577,13 @@ def register(reg) -> None:
535
577
  with scoped_home(profile_home_param(params)):
536
578
  return {"providers": registry()}
537
579
 
580
+ @reg.method("providers.nous_account")
581
+ def nous_account_(ctx: CallContext, params: dict) -> dict:
582
+ from . import nous_account
583
+ home = profile_home_param(params)
584
+ with scoped_home(home):
585
+ return {"nous_account": nous_account.read(home)}
586
+
538
587
  @reg.method("providers.auth_status")
539
588
  def auth(ctx: CallContext, params: dict) -> dict:
540
589
  with scoped_home(profile_home_param(params)):
@@ -547,7 +596,8 @@ def register(reg) -> None:
547
596
  raise InvalidParams("provider is required")
548
597
  with scoped_home(profile_home_param(params)):
549
598
  ids, fallback = model_ids(provider, force_refresh=bool(params.get("force_refresh", False)))
550
- return {"provider": provider, "model_ids": ids, "fallback": fallback}
599
+ return {"provider": provider, "model_ids": ids, "fallback": fallback,
600
+ **model_allowance_snapshot(provider, force_refresh=bool(params.get("force_refresh", False)))}
551
601
 
552
602
  @reg.method("providers.local_models")
553
603
  def local(ctx: CallContext, params: dict) -> dict:
@@ -0,0 +1,177 @@
1
+ """Read the reviewed Hermetic store without executing its API or migrating legacy data."""
2
+ from contextlib import contextmanager
3
+ from datetime import datetime, timezone
4
+ import difflib
5
+ import hashlib
6
+ import itertools
7
+ import json
8
+ import os
9
+ from pathlib import Path
10
+ import re
11
+ import stat
12
+
13
+ from ..errors import InvalidParams
14
+ from . import dashboard_plugins
15
+
16
+ _PIN = 'f7026c949d8831b26910f2ebd3434e8c58cdff89'
17
+ _SOURCES = {
18
+ '__init__.py': '9dfb815be185965bf06c7c5a0fec401f6f376569d1a6830497502898fffcf01d',
19
+ 'plugin.yaml': 'b4fbd03f70f50d2cc391e530b3e4079ecbe249ab6e5c2e4702d475911327b50e',
20
+ 'dashboard/manifest.json': '466cada1eb3345f6fa7e12a5eaef44f8a19bb02546b9456fa0576d81ff89b6c1',
21
+ 'dashboard/plugin_api.py': '23f1c612559f0086ff5c7da6d3cc8fe0c596a05c6f6eaa89db94c8c4d8c99d1d',
22
+ }
23
+ _NAME = re.compile(r'[A-Za-z0-9][A-Za-z0-9._ -]{0,127}')
24
+ _FILE = re.compile(r'([a-f0-9]{16})-SKILL[.]md')
25
+ _MAX_TEXT = 32 * 1024
26
+ _MAX_REVISIONS = 64
27
+
28
+
29
+ @contextmanager
30
+ def _directory(anchor, parts=()):
31
+ """Hold every traversal no-follow, including the profile's ancestors, through the read."""
32
+ anchor = Path(anchor).absolute()
33
+ components = (*anchor.parts[1:], *parts)
34
+ if any(p in ('', '.', '..') or '/' in p or '\\' in p for p in components):
35
+ raise ValueError('Invalid history path')
36
+ fd = os.open(anchor.anchor, os.O_RDONLY | os.O_DIRECTORY | os.O_NOFOLLOW)
37
+ try:
38
+ for part in components:
39
+ child = os.open(part, os.O_RDONLY | os.O_DIRECTORY | os.O_NOFOLLOW, dir_fd=fd)
40
+ os.close(fd)
41
+ fd = child
42
+ yield fd
43
+ finally:
44
+ os.close(fd)
45
+
46
+
47
+ def _read(fd, name, limit):
48
+ child = os.open(name, os.O_RDONLY | os.O_NOFOLLOW | os.O_NONBLOCK, dir_fd=fd)
49
+ with os.fdopen(child, 'rb') as file:
50
+ info = os.fstat(file.fileno())
51
+ if not stat.S_ISREG(info.st_mode) or info.st_size > limit:
52
+ raise ValueError('History file is too large or not regular')
53
+ data = file.read(limit + 1)
54
+ if len(data) > limit:
55
+ raise ValueError('History file is too large')
56
+ return data, info.st_mtime
57
+
58
+
59
+ def _timestamp(value):
60
+ try:
61
+ date = datetime.fromtimestamp(value, timezone.utc) if type(value) in (int, float) else datetime.fromisoformat(value.replace('Z', '+00:00'))
62
+ return date.astimezone(timezone.utc).isoformat() if date.tzinfo else None
63
+ except (TypeError, ValueError, OverflowError, OSError, AttributeError):
64
+ return None
65
+
66
+
67
+ def _result(state, reason=None, **fields):
68
+ return dict(state=state, reason=reason, backend_revision=None, revisions=[], selected=None,
69
+ comparison=None, replay_available=False) | fields
70
+
71
+
72
+ def _identity(catalog, name):
73
+ entries = catalog(skip_disabled=True, include_hidden=True)
74
+ matches = [entry for entry in entries if entry.get('load_name') == name]
75
+ if len(matches) != 1:
76
+ return None
77
+ selected = matches[0]
78
+ declared = selected.get('name')
79
+ # Hermetic keys storage by declared name; two catalog copies cannot be attributed safely.
80
+ if not isinstance(declared, str) or not _NAME.fullmatch(declared) or '..' in declared:
81
+ return None
82
+ return selected if len([entry for entry in entries if entry.get('name') == declared]) == 1 else None
83
+
84
+
85
+ def inspect_revisions(home, name, revision=None, compare_to=None):
86
+ from .skills import _skill_helper
87
+
88
+ if not isinstance(name, str) or not 0 < len(name) <= 256:
89
+ raise InvalidParams('Invalid skill identity')
90
+ if any(v is not None and (not isinstance(v, str) or not re.fullmatch('[a-f0-9]{64}', v)) for v in (revision, compare_to)):
91
+ raise InvalidParams('Invalid revision identity')
92
+ if not getattr(os, 'O_NOFOLLOW', 0) or not dashboard_plugins.reviewed_producer(home, 'hermetic', _PIN, _SOURCES):
93
+ return _result('unavailable', 'backend_unavailable')
94
+ try:
95
+ catalog = _skill_helper('skill_catalog')
96
+ selected = _identity(catalog, name) if catalog else None
97
+ if selected is None:
98
+ return _result('unavailable', 'identity_unavailable')
99
+ declared = selected['name']
100
+ local = Path(selected['path']).relative_to(home / 'skills')
101
+ if local.name != 'SKILL.md':
102
+ raise ValueError('Not a local skill')
103
+ with _directory(home, ('skills', *local.parts[:-1])) as fd:
104
+ current, _ = _read(fd, 'SKILL.md', _MAX_TEXT)
105
+ provenance = {}
106
+ with _directory(home, ('skills',)) as fd:
107
+ try:
108
+ ledger, _ = _read(fd, '.curator_ledger.jsonl', 256 * 1024)
109
+ except FileNotFoundError:
110
+ ledger = b''
111
+ for line in ledger.decode('utf-8').splitlines():
112
+ row = json.loads(line)
113
+ if not isinstance(row, dict):
114
+ raise ValueError('Invalid ledger')
115
+ if row.get('skill') == declared:
116
+ after = row.get('after') or []
117
+ if not isinstance(after, list):
118
+ raise ValueError('Invalid ledger provenance')
119
+ for item in after:
120
+ if isinstance(item, dict) and isinstance(item.get('sha256'), str):
121
+ actor = row.get('actor')
122
+ actor = actor if isinstance(actor, str) and len(actor) <= 80 and not any(ord(c) < 32 for c in actor) else None
123
+ provenance[item['sha256']] = (_timestamp(row.get('ts')), actor)
124
+ try:
125
+ with _directory(home, ('hermetic', 'skill-versions', declared)) as fd:
126
+ with os.scandir(fd) as iterator:
127
+ files = list(itertools.islice(iterator, _MAX_REVISIONS + 1))
128
+ if len(files) > _MAX_REVISIONS:
129
+ raise ValueError('Too many revisions')
130
+ rows = []
131
+ for file in files:
132
+ match = _FILE.fullmatch(file.name)
133
+ if not match:
134
+ continue
135
+ data, modified = _read(fd, file.name, _MAX_TEXT)
136
+ sha = hashlib.sha256(data).hexdigest()
137
+ if not sha.startswith(match[1]):
138
+ raise ValueError('Revision hash does not match saved bytes')
139
+ text = data.decode('utf-8')
140
+ if len(text.splitlines()) > 512:
141
+ raise ValueError('Too many revision lines')
142
+ saved_at, actor = provenance.get(sha, (_timestamp(modified), None))
143
+ identity = hashlib.sha256(json.dumps([str(home), name, sha]).encode()).hexdigest()
144
+ rows.append(dict(id=identity, sha256=sha, label=sha[:12], saved_at=saved_at, actor=actor,
145
+ current=sha == hashlib.sha256(current).hexdigest(), content=text))
146
+ except FileNotFoundError:
147
+ rows = []
148
+ if not rows:
149
+ if revision or compare_to:
150
+ raise InvalidParams('Revision no longer exists; reload history')
151
+ return _result('missing', 'history_unavailable', backend_revision=_PIN)
152
+ rows.sort(key=lambda row: (row['saved_at'] or '', row['sha256']), reverse=True)
153
+ by_id = {row['id']: row for row in rows}
154
+ target = by_id.get(revision) if revision else rows[0]
155
+ if target is None:
156
+ raise InvalidParams('Revision no longer exists; reload history')
157
+ source = by_id.get(compare_to) if compare_to else next((r for r in rows if r['id'] != target['id']), None)
158
+ if compare_to and source is None:
159
+ raise InvalidParams('Revision no longer exists; reload history')
160
+ comparison = None
161
+ if source:
162
+ lines = difflib.unified_diff(source['content'].splitlines(keepends=True), target['content'].splitlines(keepends=True),
163
+ fromfile=source['label'], tofile=target['label'])
164
+ diff = ''.join(line if line.endswith('\n') else line + '\n\\n' for line in lines)
165
+ comparison = dict(from_revision=source['id'], to_revision=target['id'], diff=diff)
166
+ # Native admission can be revoked while filesystem reads are in progress.
167
+ if not dashboard_plugins.reviewed_producer(home, 'hermetic', _PIN, _SOURCES):
168
+ return _result('unavailable', 'backend_unavailable')
169
+ if _identity(catalog, name) != selected:
170
+ return _result('unavailable', 'identity_unavailable')
171
+ return dict(state='available', reason=None, backend_revision=_PIN,
172
+ revisions=[{k: v for k, v in row.items() if k != 'content'} for row in rows],
173
+ selected=dict(revision=target['id'], content=target['content']), comparison=comparison, replay_available=False)
174
+ except InvalidParams:
175
+ raise
176
+ except (ImportError, AttributeError, OSError, ValueError, TypeError, KeyError):
177
+ return _result('unavailable', 'invalid_history')
@@ -300,6 +300,16 @@ def view_skill(profile_home: Path, name: str) -> dict:
300
300
 
301
301
 
302
302
  def register(registry) -> None:
303
+ @registry.method("skills.revisions")
304
+ def revisions(ctx: CallContext, params: dict) -> dict:
305
+ from .skill_revisions import inspect_revisions
306
+ home = profile_home_param(params)
307
+ ctx.check_cancelled()
308
+ with scoped_home(home, load_plugins=False, recover_processes=False):
309
+ result = inspect_revisions(home, params.get('name'), params.get('revision'), params.get('compare_to'))
310
+ ctx.check_cancelled()
311
+ return result
312
+
303
313
  @registry.method("skills.list")
304
314
  def list_(ctx: CallContext, params: dict) -> dict:
305
315
  home = profile_home_param(params)
@@ -0,0 +1,67 @@
1
+ """``tts.synthesize``: bounded audio through the Agent's own speech providers."""
2
+ from __future__ import annotations
3
+
4
+ import base64
5
+ import json
6
+ import math
7
+ import tempfile
8
+ from pathlib import Path
9
+
10
+ from ..errors import InvalidParams, RpcError
11
+ from ..home import profile_home_param, scoped_home
12
+ from ..rpc import CallContext
13
+
14
+ MAX_AUDIO_BYTES = 8 * 1024 * 1024
15
+
16
+
17
+ def synthesize(text: str, provider: str, speed: float | None = None) -> dict:
18
+ from tools import tts_tool
19
+
20
+ if (provider != 'edge' and provider not in tts_tool._BUILTIN_DISPATCH
21
+ and tts_tool._resolve_command_provider_config(provider, tts_tool._load_tts_config()) is None):
22
+ raise InvalidParams(f'unknown TTS provider {provider}')
23
+ try:
24
+ with tempfile.TemporaryDirectory(prefix='talaria-tts-') as directory:
25
+ root = Path(directory).resolve()
26
+ result = json.loads(tts_tool.text_to_speech_tool(
27
+ text, output_path=str(root / 'speech.mp3'), speed=speed, provider=provider))
28
+ if not isinstance(result, dict) or result.get('success') is not True:
29
+ message = result.get('error') if isinstance(result, dict) else None
30
+ raise ValueError(str(message or 'Agent speech generation failed'))
31
+ paths = result.get('file_paths')
32
+ if not isinstance(paths, list) or not paths:
33
+ raise ValueError('Agent returned no audio files')
34
+ audio = bytearray()
35
+ audio_format = ''
36
+ for raw_path in paths:
37
+ path = Path(raw_path).resolve()
38
+ if not path.is_relative_to(root):
39
+ raise ValueError('Agent audio escaped the temporary directory')
40
+ suffix = path.suffix.lower().lstrip('.')
41
+ if suffix not in ('mp3', 'wav', 'flac') or (len(paths) > 1 and suffix != 'mp3'):
42
+ raise ValueError('Agent returned unsupported audio parts')
43
+ audio_format = suffix
44
+ with path.open('rb') as source:
45
+ part = source.read(MAX_AUDIO_BYTES - len(audio) + 1)
46
+ if not part or len(audio) + len(part) > MAX_AUDIO_BYTES:
47
+ raise ValueError('Agent audio is empty or exceeds 8 MiB')
48
+ audio.extend(part)
49
+ return {'provider': str(result.get('provider') or provider), 'format': audio_format,
50
+ 'audio_b64': base64.b64encode(audio).decode('ascii')}
51
+ except Exception as error:
52
+ raise RpcError(str(error), condition='tts_failed') from error
53
+
54
+
55
+ def register(registry) -> None:
56
+ @registry.method('tts.synthesize')
57
+ def synthesize_(ctx: CallContext, params: dict) -> dict:
58
+ text, provider, speed = params.get('text'), params.get('provider'), params.get('speed')
59
+ if not isinstance(text, str) or not text.strip() or len(text) > 5000:
60
+ raise InvalidParams('text must contain 1 to 5000 characters')
61
+ if not isinstance(provider, str) or not provider.strip():
62
+ raise InvalidParams('provider is required')
63
+ if speed is not None and (isinstance(speed, bool) or not isinstance(speed, (int, float))
64
+ or not math.isfinite(speed) or not 0.5 <= speed <= 2):
65
+ raise InvalidParams('speed must be a number from 0.5 to 2')
66
+ with scoped_home(profile_home_param(params)):
67
+ return synthesize(text, provider, speed)
@@ -74,7 +74,10 @@ class CallContext:
74
74
  class RpcServer:
75
75
  def __init__(self, methods: dict[str, Handler], *, stdin=None, stdout=None, max_calls: int = DEFAULT_MAX_CALLS):
76
76
  self.methods = dict(methods)
77
- self._slots = threading.BoundedSemaphore(max(1, int(max_calls)))
77
+ call_limit = max(1, int(max_calls))
78
+ self._slots = threading.BoundedSemaphore(call_limit)
79
+ # A parked command must leave room for its answer and unrelated Agent work.
80
+ self._command_slots = threading.BoundedSemaphore(min(8, call_limit - 1))
78
81
  self.methods.setdefault("rpc.cancel", self._cancel)
79
82
  self.methods.setdefault("rpc.methods", lambda ctx, params: {"methods": sorted(self.methods)})
80
83
  self._in = stdin or sys.stdin.buffer
@@ -256,7 +259,11 @@ class RpcServer:
256
259
  # Cancellation must not queue behind the call it targets.
257
260
  self._dispatch(request)
258
261
  continue
259
- if not self._slots.acquire(blocking=False):
262
+ command = request.get("method") == "commands.exec"
263
+ command_admitted = not command or self._command_slots.acquire(blocking=False)
264
+ if not command_admitted or not self._slots.acquire(blocking=False):
265
+ if command and command_admitted:
266
+ self._command_slots.release()
260
267
  if request.get("method") == "chat.start":
261
268
  StartupTiming(request).finish("refused")
262
269
  self._error(request.get("id"), APPLICATION_ERROR, "sidecar is at its concurrent call limit", {"condition": "sidecar_busy"})
@@ -279,3 +286,5 @@ class RpcServer:
279
286
  self._dispatch(request, ctx)
280
287
  finally:
281
288
  self._slots.release()
289
+ if request.get("method") == "commands.exec":
290
+ self._command_slots.release()