thursday-agent 0.5.0 → 0.7.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 (667) hide show
  1. package/.next/BUILD_ID +1 -1
  2. package/.next/app-path-routes-manifest.json +3 -2
  3. package/.next/build-manifest.json +3 -3
  4. package/.next/prerender-manifest.json +3 -3
  5. package/.next/required-server-files.json +8 -1
  6. package/.next/routes-manifest.json +18 -6
  7. package/.next/server/app/_global-error/page.js.nft.json +1 -1
  8. package/.next/server/app/_global-error.html +1 -1
  9. package/.next/server/app/_global-error.rsc +1 -1
  10. package/.next/server/app/_global-error.segments/__PAGE__.segment.rsc +1 -1
  11. package/.next/server/app/_global-error.segments/_full.segment.rsc +1 -1
  12. package/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  13. package/.next/server/app/_not-found/page.js.nft.json +1 -1
  14. package/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
  15. package/.next/server/app/_not-found.html +1 -1
  16. package/.next/server/app/_not-found.rsc +13 -13
  17. package/.next/server/app/_not-found.segments/_full.segment.rsc +13 -13
  18. package/.next/server/app/_not-found.segments/_not-found/__PAGE__.segment.rsc +12 -12
  19. package/.next/server/app/_not-found.segments/_tree.segment.rsc +2 -2
  20. package/.next/server/app/api/artifact/route.js +10 -6
  21. package/.next/server/app/api/artifact/route.js.nft.json +1 -1
  22. package/.next/server/app/api/bot/memory/files/route.js +5 -4
  23. package/.next/server/app/api/bot/memory/files/route.js.nft.json +1 -1
  24. package/.next/server/app/api/bot/memory/route.js +8 -8
  25. package/.next/server/app/api/bot/memory/route.js.nft.json +1 -1
  26. package/.next/server/app/api/bot/route.js +8 -8
  27. package/.next/server/app/api/bot/route.js.nft.json +1 -1
  28. package/.next/server/app/api/bot/thread/[id]/route/app-paths-manifest.json +3 -0
  29. package/.next/server/app/api/bot/thread/[id]/route.js +15 -0
  30. package/.next/server/app/api/bot/thread/[id]/route.js.nft.json +1 -0
  31. package/.next/server/app/api/bot/thread/[id]/route_client-reference-manifest.js +3 -0
  32. package/.next/server/app/api/bot/thread/route/app-paths-manifest.json +3 -0
  33. package/.next/server/app/api/bot/thread/route.js +15 -0
  34. package/.next/server/app/api/bot/thread/route.js.nft.json +1 -0
  35. package/.next/server/app/api/bot/thread/route_client-reference-manifest.js +3 -0
  36. package/.next/server/app/api/config/route.js +7 -7
  37. package/.next/server/app/api/config/route.js.nft.json +1 -1
  38. package/.next/server/app/api/events/route.js +3 -3
  39. package/.next/server/app/api/events/route.js.nft.json +1 -1
  40. package/.next/server/app/api/file/[...path]/route.js +4 -4
  41. package/.next/server/app/api/file/[...path]/route.js.nft.json +1 -1
  42. package/.next/server/app/api/llm-model/catalog/route.js +8 -8
  43. package/.next/server/app/api/llm-model/catalog/route.js.nft.json +1 -1
  44. package/.next/server/app/api/llm-model/credits/route.js +8 -8
  45. package/.next/server/app/api/llm-model/credits/route.js.nft.json +1 -1
  46. package/.next/server/app/api/llm-model/route.js +8 -8
  47. package/.next/server/app/api/llm-model/route.js.nft.json +1 -1
  48. package/.next/server/app/api/llm-model/subscription/route.js +8 -8
  49. package/.next/server/app/api/llm-model/subscription/route.js.nft.json +1 -1
  50. package/.next/server/app/api/mcp/[name]/route.js +6 -6
  51. package/.next/server/app/api/mcp/[name]/route.js.nft.json +1 -1
  52. package/.next/server/app/api/mcp/oauth/callback/route.js +4 -4
  53. package/.next/server/app/api/mcp/oauth/callback/route.js.nft.json +1 -1
  54. package/.next/server/app/api/mcp/route.js +6 -6
  55. package/.next/server/app/api/mcp/route.js.nft.json +1 -1
  56. package/.next/server/app/api/mcp/tools/route.js +6 -6
  57. package/.next/server/app/api/mcp/tools/route.js.nft.json +1 -1
  58. package/.next/server/app/api/memory/edit/route.js +15 -15
  59. package/.next/server/app/api/memory/edit/route.js.nft.json +1 -1
  60. package/.next/server/app/api/memory/route.js +7 -6
  61. package/.next/server/app/api/memory/route.js.nft.json +1 -1
  62. package/.next/server/app/api/skills/[source]/[name]/route.js +6 -6
  63. package/.next/server/app/api/skills/[source]/[name]/route.js.nft.json +1 -1
  64. package/.next/server/app/api/skills/route.js +6 -6
  65. package/.next/server/app/api/skills/route.js.nft.json +1 -1
  66. package/.next/server/app/api/thursday/call/route.js +10 -11
  67. package/.next/server/app/api/thursday/call/route.js.nft.json +1 -1
  68. package/.next/server/app/api/thursday/skills/route.js +9 -10
  69. package/.next/server/app/api/thursday/skills/route.js.nft.json +1 -1
  70. package/.next/server/app/api/thursday/tool-call/route.js +15 -15
  71. package/.next/server/app/api/thursday/tool-call/route.js.nft.json +1 -1
  72. package/.next/server/app/api/workspace/missing/route/app-paths-manifest.json +3 -0
  73. package/.next/server/app/api/workspace/missing/route/build-manifest.json +12 -0
  74. package/.next/server/app/api/workspace/missing/route/server-reference-manifest.json +4 -0
  75. package/.next/server/app/api/workspace/missing/route.js +12 -0
  76. package/.next/server/app/api/workspace/missing/route.js.map +5 -0
  77. package/.next/server/app/api/workspace/missing/route.js.nft.json +1 -0
  78. package/.next/server/app/api/workspace/missing/route_client-reference-manifest.js +3 -0
  79. package/.next/server/app/api/workspace/route.js +5 -5
  80. package/.next/server/app/api/workspace/route.js.nft.json +1 -1
  81. package/.next/server/app/artifact/[...path]/page/server-reference-manifest.json +1 -1
  82. package/.next/server/app/artifact/[...path]/page.js +4 -3
  83. package/.next/server/app/artifact/[...path]/page.js.nft.json +1 -1
  84. package/.next/server/app/artifact/[...path]/page_client-reference-manifest.js +1 -1
  85. package/.next/server/app/favicon.ico/route.js.nft.json +1 -1
  86. package/.next/server/app/page/server-reference-manifest.json +67 -45
  87. package/.next/server/app/page.js +11 -9
  88. package/.next/server/app/page.js.nft.json +1 -1
  89. package/.next/server/app/page_client-reference-manifest.js +1 -1
  90. package/.next/server/app-paths-manifest.json +3 -2
  91. package/.next/server/chunks/[root-of-the-server]__0-06t3f._.js +8 -0
  92. package/.next/server/chunks/[root-of-the-server]__02846fb._.js +8 -0
  93. package/.next/server/chunks/[root-of-the-server]__05luceg._.js +3 -0
  94. package/.next/server/chunks/[root-of-the-server]__06--3q3._.js +8 -0
  95. package/.next/server/chunks/[root-of-the-server]__06l05n_._.js +3 -0
  96. package/.next/server/chunks/[root-of-the-server]__07bnah_._.js +3 -0
  97. package/.next/server/chunks/[root-of-the-server]__08eae20._.js +8 -0
  98. package/.next/server/chunks/[root-of-the-server]__0_ue8oe._.js +3 -0
  99. package/.next/server/chunks/[root-of-the-server]__0btqrct._.js +3 -0
  100. package/.next/server/chunks/[root-of-the-server]__0c9fgca._.js +5 -0
  101. package/.next/server/chunks/[root-of-the-server]__0h_x6q6._.js +5 -0
  102. package/.next/server/chunks/{[root-of-the-server]__0pa2n68._.js → [root-of-the-server]__0kxrvxf._.js} +2 -2
  103. package/.next/server/chunks/{[root-of-the-server]__0q0vvt2._.js → [root-of-the-server]__0ov3iir._.js} +2 -2
  104. package/.next/server/chunks/[root-of-the-server]__0qwtlmx._.js +8 -0
  105. package/.next/server/chunks/[root-of-the-server]__0sm5xvm._.js +3 -0
  106. package/.next/server/chunks/[root-of-the-server]__0zp35ul._.js +5 -0
  107. package/.next/server/chunks/[root-of-the-server]__144u9d_._.js +3 -0
  108. package/.next/server/chunks/[root-of-the-server]__18-2tsq._.js +5 -0
  109. package/.next/server/chunks/[root-of-the-server]__1e-ci13._.js +3 -0
  110. package/.next/server/chunks/[root-of-the-server]__1e2365e._.js +8 -0
  111. package/.next/server/chunks/[root-of-the-server]__1fix932._.js +8 -0
  112. package/.next/server/chunks/{[root-of-the-server]__0ce8nf8._.js → [root-of-the-server]__1g3t7vn._.js} +3 -3
  113. package/.next/server/chunks/[root-of-the-server]__1kp-83u._.js +5 -0
  114. package/.next/server/chunks/[root-of-the-server]__1kv8p3e._.js +5 -0
  115. package/.next/server/chunks/[root-of-the-server]__1orn-5b._.js +2 -3
  116. package/.next/server/chunks/_02szwk8._.js +5 -0
  117. package/.next/server/chunks/_05h2cii._.js +1 -1
  118. package/.next/server/chunks/_06c9kie._.js +216 -0
  119. package/.next/server/chunks/{_1x6kd1r._.js → _07y2gj-._.js} +1 -1
  120. package/.next/server/chunks/_0a43a-0._.js +3 -0
  121. package/.next/server/chunks/_0bujjey._.js +5 -0
  122. package/.next/server/chunks/_0c9j6rb._.js +1 -1
  123. package/.next/server/chunks/_0dkd549._.js +3 -0
  124. package/.next/server/chunks/_0ej1kvv._.js +3 -0
  125. package/.next/server/chunks/_0f6ts7z._.js +3 -0
  126. package/.next/server/chunks/_0gm9hyv._.js +55 -0
  127. package/.next/server/chunks/_0i55en5._.js +25 -0
  128. package/.next/server/chunks/_0k50n27._.js +18 -0
  129. package/.next/server/chunks/_0khihjk._.js +3 -3
  130. package/.next/server/chunks/_0n74zsf._.js +5 -5
  131. package/.next/server/chunks/_0nvm9ef._.js +3 -0
  132. package/.next/server/chunks/_0p56fn0._.js +3 -0
  133. package/.next/server/chunks/_0recufk._.js +1 -1
  134. package/.next/server/chunks/_0xbkz10._.js +3 -0
  135. package/.next/server/chunks/_10tkr26._.js +3 -0
  136. package/.next/server/chunks/{_0ioz3nd._.js → _11u2kp7._.js} +1 -1
  137. package/.next/server/chunks/_11ujpya._.js +3 -0
  138. package/.next/server/chunks/_127nx_p._.js +5 -0
  139. package/.next/server/chunks/_17l5ygt._.js +1 -1
  140. package/.next/server/chunks/_19uauj6._.js +3 -0
  141. package/.next/server/chunks/_1_5mnq4._.js +5 -5
  142. package/.next/server/chunks/_1abl6t9._.js +55 -0
  143. package/.next/server/chunks/_1d0j961._.js +3 -3
  144. package/.next/server/chunks/_1dbixxz._.js +3 -0
  145. package/.next/server/chunks/_1dc_d1q._.js +98 -0
  146. package/.next/server/chunks/_1drgfx4._.js +5 -5
  147. package/.next/server/chunks/_1e48czp._.js +3 -3
  148. package/.next/server/chunks/_1f31u5x._.js +5 -0
  149. package/.next/server/chunks/_1gnjfli._.js +3 -0
  150. package/.next/server/chunks/_1kg70wc._.js +3 -3
  151. package/.next/server/chunks/_1klbcft._.js +5 -0
  152. package/.next/server/chunks/_1krd9rf._.js +4 -1
  153. package/.next/server/chunks/_1kwmzab._.js +3 -0
  154. package/.next/server/chunks/{_1pf4qe-._.js → _1oxj9fa._.js} +1 -1
  155. package/.next/server/chunks/{_1f46eie._.js → _1pcmdbb._.js} +1 -1
  156. package/.next/server/chunks/_1qgix-j._.js +3 -0
  157. package/.next/server/chunks/{lib_logger_ts_1exwjut._.js → _1rpchta._.js} +5 -5
  158. package/.next/server/chunks/_1vsej-s._.js +5 -0
  159. package/.next/server/chunks/_1yx0p_s._.js +5 -0
  160. package/.next/server/chunks/{_0rnf-6n._.js → _20fsr_z._.js} +6 -6
  161. package/.next/server/chunks/_2128hkj._.js +5 -0
  162. package/.next/server/chunks/_next-internal_server_app_api_bot_thread_[id]_route_actions_1fstjn2.js +3 -0
  163. package/.next/server/chunks/_next-internal_server_app_api_bot_thread_route_actions_003ccso.js +3 -0
  164. package/.next/server/chunks/_next-internal_server_app_api_workspace_missing_route_actions_1fidi6p.js +3 -0
  165. package/.next/server/chunks/config_ts_1g4sz5o._.js +1 -1
  166. package/.next/server/chunks/features_0-cnt0l._.js +4 -0
  167. package/.next/server/chunks/features_0hdaci0._.js +4 -0
  168. package/.next/server/chunks/features_1e39j7-._.js +8 -0
  169. package/.next/server/chunks/features_bot_bot_query_ts_12mgkl2._.js +1 -1
  170. package/.next/server/chunks/features_memory_1uqvksn._.js +1 -1
  171. package/.next/server/chunks/{node_modules_consola_dist_chunks_prompt_mjs_0v_7drq._.js → node_modules_consola_dist_chunks_prompt_mjs_0a7-pbw._.js} +1 -1
  172. package/.next/server/chunks/{node_modules_consola_dist_chunks_prompt_mjs_17k8irj._.js → node_modules_consola_dist_chunks_prompt_mjs_0gzvgfv._.js} +1 -1
  173. package/.next/server/chunks/{node_modules_consola_dist_chunks_prompt_mjs_0i7cvml._.js → node_modules_consola_dist_chunks_prompt_mjs_107pxfn._.js} +1 -1
  174. package/.next/server/chunks/{node_modules_consola_dist_chunks_prompt_mjs_0icqaqw._.js → node_modules_consola_dist_chunks_prompt_mjs_15hbel8._.js} +1 -1
  175. package/.next/server/chunks/node_modules_consola_dist_chunks_prompt_mjs_18i-23e._.js +3 -0
  176. package/.next/server/chunks/node_modules_consola_dist_chunks_prompt_mjs_1bewgf3._.js +3 -0
  177. package/.next/server/chunks/node_modules_consola_dist_chunks_prompt_mjs_1nlww1m._.js +3 -0
  178. package/.next/server/chunks/node_modules_consola_dist_chunks_prompt_mjs_1q77nfx._.js +3 -0
  179. package/.next/server/chunks/node_modules_consola_dist_chunks_prompt_mjs_1xqdzx_._.js +3 -0
  180. package/.next/server/chunks/{node_modules_zod_v4_1801ax7._.js → node_modules_zod_v4_0lkux5-._.js} +2 -2
  181. package/.next/server/chunks/{node_modules_zod_v4_1cha_bw._.js → node_modules_zod_v4_1jmr9cq._.js} +2 -2
  182. package/.next/server/chunks/{node_modules_zod_v4_0ubdflj._.js → node_modules_zod_v4_1yrxmek._.js} +2 -2
  183. package/.next/server/chunks/node_modules_zod_v4_classic_errors_0tp0y-q.js +3 -0
  184. package/.next/server/chunks/ssr/[root-of-the-server]__0-e011f._.js +3 -0
  185. package/.next/server/chunks/ssr/[root-of-the-server]__09q9med._.js +1 -1
  186. package/.next/server/chunks/ssr/[root-of-the-server]__0lyi8i2._.js +1 -1
  187. package/.next/server/chunks/ssr/[root-of-the-server]__0pd8yr7._.js +3 -0
  188. package/.next/server/chunks/ssr/[root-of-the-server]__16jc196._.js +1 -1
  189. package/.next/server/chunks/ssr/[root-of-the-server]__18dthbp._.js +3 -0
  190. package/.next/server/chunks/ssr/[root-of-the-server]__18e68w8._.js +3 -0
  191. package/.next/server/chunks/ssr/[root-of-the-server]__1mzi-ju._.js +1 -1
  192. package/.next/server/chunks/ssr/[root-of-the-server]__1nygfik._.js +5 -0
  193. package/.next/server/chunks/ssr/[root-of-the-server]__1sdphb0._.js +8 -0
  194. package/.next/server/chunks/ssr/[root-of-the-server]__1vdmfbe._.js +3 -0
  195. package/.next/server/chunks/ssr/[root-of-the-server]__1waa3rc._.js +85 -0
  196. package/.next/server/chunks/ssr/_0-2qsxo._.js +3 -0
  197. package/.next/server/chunks/ssr/_00rehl_._.js +3 -0
  198. package/.next/server/chunks/ssr/{_1lz_cq2._.js → _02oc_h5._.js} +76 -97
  199. package/.next/server/chunks/ssr/_05yghx6._.js +3 -0
  200. package/.next/server/chunks/ssr/_07nbwap._.js +3 -0
  201. package/.next/server/chunks/ssr/_08c4z-9._.js +3 -0
  202. package/.next/server/chunks/ssr/_0_qfdlw._.js +4 -0
  203. package/.next/server/chunks/ssr/{_0m2lsd1._.js → _0b6_jv-._.js} +2 -2
  204. package/.next/server/chunks/ssr/_0evkpto._.js +3 -0
  205. package/.next/server/chunks/ssr/_0geg212._.js +3 -0
  206. package/.next/server/chunks/ssr/{_1jdgjv9._.js → _0hxt2ul._.js} +2 -2
  207. package/.next/server/chunks/ssr/_0i_6q1w._.js +2 -2
  208. package/.next/server/chunks/ssr/_0lu1n_x._.js +1 -1
  209. package/.next/server/chunks/ssr/_0no7i1o._.js +3 -0
  210. package/.next/server/chunks/ssr/_0tzg--b._.js +3 -0
  211. package/.next/server/chunks/ssr/{_15j2_8f._.js → _0wzaht-._.js} +2 -2
  212. package/.next/server/chunks/ssr/_0z-g0uy._.js +3 -0
  213. package/.next/server/chunks/ssr/_114ylv7._.js +7 -0
  214. package/.next/server/chunks/ssr/_123y-ah._.js +3 -0
  215. package/.next/server/chunks/ssr/_12c-iwh._.js +3 -0
  216. package/.next/server/chunks/ssr/_12w42gi._.js +3 -0
  217. package/.next/server/chunks/ssr/_161kqav._.js +3 -0
  218. package/.next/server/chunks/ssr/_167hchk._.js +3 -0
  219. package/.next/server/chunks/ssr/{_0ap2fzn._.js → _16c6_xm._.js} +2 -2
  220. package/.next/server/chunks/ssr/_18opah7._.js +3 -0
  221. package/.next/server/chunks/ssr/_1_krfph._.js +3 -0
  222. package/.next/server/chunks/ssr/{_0rzucul._.js → _1_x5spz._.js} +3 -3
  223. package/.next/server/chunks/ssr/_1a61fc9._.js +3 -0
  224. package/.next/server/chunks/ssr/_1ey7qn-._.js +70 -0
  225. package/.next/server/chunks/ssr/_1g9vs7q._.js +3 -0
  226. package/.next/server/chunks/ssr/_1jmz33w._.js +3 -0
  227. package/.next/server/chunks/ssr/_1rgtxhr._.js +5 -0
  228. package/.next/server/chunks/ssr/_1slp25y._.js +3 -0
  229. package/.next/server/chunks/ssr/_1w_t7h7._.js +101 -0
  230. package/.next/server/chunks/ssr/{_0s99bgb._.js → _1wyfaq_._.js} +9 -3
  231. package/.next/server/chunks/ssr/_200gt-m._.js +102 -0
  232. package/.next/server/chunks/ssr/components_ui_tabs_tsx_0ej40b4._.js +3 -0
  233. package/.next/server/chunks/ssr/features_bot_thread_query_ts_023eklt._.js +4 -0
  234. package/.next/server/chunks/ssr/features_config_components_config-setting_tsx_0xfwqdg._.js +1 -1
  235. package/.next/server/chunks/ssr/features_connectors_components_mcp-setting_tsx_0jmbgvp._.js +1 -1
  236. package/.next/server/chunks/ssr/features_workspace_00jz2hu._.js +8 -0
  237. package/.next/server/chunks/ssr/{_1-teee5._.js → lib_logger_ts_0-olsze._.js} +2 -7
  238. package/.next/server/chunks/ssr/{node_modules_05-n6dz._.js → node_modules_02ai7br._.js} +1 -1
  239. package/.next/server/chunks/ssr/{node_modules_1chvq5f._.js → node_modules_02deexj._.js} +1 -1
  240. package/.next/server/chunks/ssr/{node_modules_0m383r2._.js → node_modules_07za262._.js} +1 -1
  241. package/.next/server/chunks/ssr/{node_modules_07dsgkx._.js → node_modules_0_s9get._.js} +1 -1
  242. package/.next/server/chunks/ssr/{node_modules_1a0kmjl._.js → node_modules_0n3c7h0._.js} +1 -1
  243. package/.next/server/chunks/ssr/{node_modules_0zeg3x_._.js → node_modules_0od6jwr._.js} +1 -1
  244. package/.next/server/chunks/ssr/{node_modules_1y79i83._.js → node_modules_0rdt7pk._.js} +1 -1
  245. package/.next/server/chunks/ssr/{node_modules_17bwo43._.js → node_modules_0tusx4d._.js} +3 -3
  246. package/.next/server/chunks/ssr/{node_modules_04sksn9._.js → node_modules_0w1z7kz._.js} +1 -1
  247. package/.next/server/chunks/ssr/{node_modules_1uyk91w._.js → node_modules_0wdupfz._.js} +1 -1
  248. package/.next/server/chunks/ssr/{node_modules_0ifp389._.js → node_modules_1720w0a._.js} +1 -1
  249. package/.next/server/chunks/ssr/{node_modules_0u9da1h._.js → node_modules_18lsg7d._.js} +1 -1
  250. package/.next/server/chunks/ssr/{node_modules_1k6n600._.js → node_modules_1b94fxf._.js} +1 -1
  251. package/.next/server/chunks/ssr/{node_modules_20c28js._.js → node_modules_1ecdo1s._.js} +1 -1
  252. package/.next/server/chunks/ssr/{node_modules_0fkeku3._.js → node_modules_1fa9ag7._.js} +1 -1
  253. package/.next/server/chunks/ssr/{node_modules_1j8j4pt._.js → node_modules_1fv-_si._.js} +1 -1
  254. package/.next/server/chunks/ssr/{node_modules_0-dr_o7._.js → node_modules_1hf461g._.js} +1 -1
  255. package/.next/server/chunks/ssr/{node_modules_1lz0oxc._.js → node_modules_1m71ta-._.js} +1 -1
  256. package/.next/server/chunks/ssr/{node_modules_1t77e4n._.js → node_modules_1n93n-g._.js} +1 -1
  257. package/.next/server/chunks/ssr/{node_modules_16mkxuo._.js → node_modules_1n9lqu9._.js} +1 -1
  258. package/.next/server/chunks/ssr/{node_modules_1k7z2j6._.js → node_modules_1npnsvd._.js} +1 -1
  259. package/.next/server/chunks/ssr/{node_modules_056qgf-._.js → node_modules_1rn2r0n._.js} +1 -1
  260. package/.next/server/chunks/ssr/{node_modules_0x3-ply._.js → node_modules_1seuurl._.js} +2 -2
  261. package/.next/server/chunks/ssr/{node_modules_0bvopy2._.js → node_modules_1vq-mfk._.js} +1 -1
  262. package/.next/server/chunks/ssr/{node_modules_0iur59s._.js → node_modules_1vzyw1t._.js} +1 -1
  263. package/.next/server/chunks/ssr/{node_modules_1k8j8n0._.js → node_modules_1w359w4._.js} +1 -1
  264. package/.next/server/chunks/ssr/{node_modules_1x0ztf4._.js → node_modules_1yajbl6._.js} +1 -1
  265. package/.next/server/chunks/ssr/{node_modules_1-y7nni._.js → node_modules_20eqhy8._.js} +1 -1
  266. package/.next/server/chunks/ssr/{node_modules_@mermaid-js_parser_dist_chunks_mermaid-parser_core_0bkwd0u._.js → node_modules_@mermaid-js_parser_dist_chunks_mermaid-parser_core_019sbis._.js} +1 -1
  267. package/.next/server/chunks/ssr/{node_modules_@mermaid-js_parser_dist_chunks_mermaid-parser_core_0p9a9su._.js → node_modules_@mermaid-js_parser_dist_chunks_mermaid-parser_core_0s6piq3._.js} +1 -1
  268. package/.next/server/chunks/ssr/{node_modules_@vercel_oidc_dist_1o553h-._.js → node_modules_@vercel_oidc_dist_05itbb1._.js} +1 -1
  269. package/.next/server/chunks/ssr/node_modules_lucide-react_dist_esm_icons_trash_mjs_0px2gzr._.js +3 -0
  270. package/.next/server/middleware-build-manifest.js +3 -3
  271. package/.next/server/pages/404.html +1 -1
  272. package/.next/server/pages/500.html +1 -1
  273. package/.next/server/server-reference-manifest.js +1 -1
  274. package/.next/server/server-reference-manifest.json +68 -46
  275. package/.next/static/chunks/07vqbk_9t4em4.js +2 -0
  276. package/.next/static/chunks/08krja1zx7nqg.js +1 -0
  277. package/.next/static/chunks/0g4b348l0pve7.js +1 -0
  278. package/.next/static/chunks/0qcuwdk132jjt.js +1 -0
  279. package/.next/static/chunks/0vlgzqo9ka90v.js +1 -0
  280. package/.next/static/chunks/{11r2yp_yh9_qn.js → 0z69gvysmave7.js} +1 -1
  281. package/.next/static/chunks/0zrupxgci5gqc.js +1 -0
  282. package/.next/static/chunks/12fvz1w5ows75.js +1 -0
  283. package/.next/static/chunks/14t03ned286iu.js +1 -0
  284. package/.next/static/chunks/156xxbkrz5lzu.js +18 -0
  285. package/.next/static/chunks/1fz14reod4lft.js +1 -0
  286. package/.next/static/chunks/1g23dbabl-vkr.js +1 -0
  287. package/.next/static/chunks/1ohslk4568tm3.js +1 -0
  288. package/.next/static/chunks/1qy_rc3oxfxok.js +1 -0
  289. package/.next/static/chunks/1sbmwswc9k2-1.js +1 -0
  290. package/.next/static/chunks/1vqezbhjm3goq.js +1 -0
  291. package/.next/static/chunks/1zea7qdl-7365.js +1 -0
  292. package/.next/static/chunks/1zvqumkg7kmo0.css +1 -0
  293. package/.next/static/chunks/26hpqt3y6bogl.js +12 -0
  294. package/.next/static/chunks/2_j5mqm6d-z18.js +99 -0
  295. package/.next/static/chunks/2dt6tu7a22svs.js +1 -0
  296. package/.next/static/chunks/2h5ls3d86kya6.js +1 -0
  297. package/.next/static/chunks/2wc6y1ht6dfuy.js +1 -0
  298. package/.next/static/chunks/{435atsnhs7ksu.js → 2xr0zpll7thyi.js} +2 -2
  299. package/.next/static/chunks/31jztc-yq30m7.js +1 -0
  300. package/.next/static/chunks/391af0i8eljzk.js +1 -0
  301. package/.next/static/chunks/3bfwpww3m3x4u.js +1 -0
  302. package/.next/static/chunks/{38gweqdo4jpfj.js → 3izg0a3k87q1-.js} +5 -5
  303. package/.next/static/chunks/3p2s2cjokx1aa.js +5 -0
  304. package/.next/static/chunks/{408ueu4hfvcg7.js → 41s3fml5oivsa.js} +1 -1
  305. package/README.md +45 -193
  306. package/app/api/events/app-event.ts +6 -4
  307. package/app/api/query-key.ts +25 -16
  308. package/bin/database.mjs +37 -0
  309. package/bin/thursday.mjs +44 -28
  310. package/components/ui/custom-icon.tsx +0 -60
  311. package/components/ui/radio-group.tsx +37 -0
  312. package/components/ui/shiny-text.tsx +33 -6
  313. package/database/migrations/{20260910173049_numerous_spirit → 20260916145701_clever_multiple_man}/migration.sql +80 -24
  314. package/database/migrations/{20260910173049_numerous_spirit → 20260916145701_clever_multiple_man}/snapshot.json +689 -110
  315. package/database/migrations/20260916160713_thread_cancelled/migration.sql +2 -0
  316. package/database/migrations/{20260911030320_opposite_jack_power → 20260916160713_thread_cancelled}/snapshot.json +706 -84
  317. package/docs/how-it-works.md +40 -35
  318. package/docs/images/keeps-going.png +0 -0
  319. package/docs/images/two-minds.png +0 -0
  320. package/docs/live-calls.md +236 -0
  321. package/docs/thread-rooms.md +71 -0
  322. package/features/ai/chatgpt.ts +1 -2
  323. package/features/ai/live.schema.ts +128 -0
  324. package/features/ai/load-tools.ts +152 -79
  325. package/features/ai/model.schema.ts +2 -120
  326. package/features/ai/model.ts +52 -88
  327. package/features/ai/prompts/bot.prompt.ts +91 -214
  328. package/features/ai/prompts/live.prompt.ts +169 -0
  329. package/features/ai/prompts/prompt-helper.ts +92 -32
  330. package/features/ai/prompts/thursday.prompt.ts +164 -190
  331. package/features/ai/tools/bot.tool.ts +38 -145
  332. package/features/ai/tools/call.tool.ts +33 -5
  333. package/features/ai/tools/connected.ts +5 -3
  334. package/features/ai/tools/mcp.tool.ts +7 -4
  335. package/features/ai/tools/memory.tool.ts +35 -31
  336. package/features/ai/tools/skills.tool.ts +11 -6
  337. package/features/ai/tools/studio.tool.ts +26 -21
  338. package/features/ai/tools/tool-name.ts +3 -5
  339. package/features/ai/tools/workspace.tool.ts +33 -10
  340. package/features/artifact/artifact.action.ts +2 -2
  341. package/features/artifact/artifact.query.ts +112 -61
  342. package/features/artifact/artifact.schema.ts +8 -6
  343. package/features/artifact/components/artifact-setting.tsx +83 -33
  344. package/features/bot/bot.action.ts +43 -36
  345. package/features/bot/bot.memory.ts +137 -20
  346. package/features/bot/bot.query.ts +28 -11
  347. package/features/bot/bot.run.ts +296 -744
  348. package/features/bot/bot.runner.ts +463 -864
  349. package/features/bot/bot.schema.ts +93 -82
  350. package/features/bot/bot.seed.ts +141 -64
  351. package/features/bot/components/bot-mark.tsx +324 -232
  352. package/features/bot/components/bot-room.tsx +1613 -697
  353. package/features/bot/components/bot-roster.tsx +8 -13
  354. package/features/bot/components/bot-setting.tsx +58 -42
  355. package/features/bot/components/bot-tool.tsx +55 -87
  356. package/features/bot/components/mark-palette.tsx +35 -32
  357. package/features/bot/components/path-chips.tsx +33 -3
  358. package/features/bot/components/thread-badge.tsx +34 -0
  359. package/features/bot/components/thread-reply.tsx +639 -0
  360. package/features/bot/components/thread-setting.tsx +674 -0
  361. package/features/bot/mark.const.ts +79 -31
  362. package/features/bot/room.query.ts +889 -0
  363. package/features/bot/room.schema.ts +64 -0
  364. package/features/bot/seed-bots.ts +2 -1
  365. package/features/bot/thread.query.ts +971 -0
  366. package/features/bot/thread.store.ts +587 -0
  367. package/features/config/components/voice-key.tsx +113 -88
  368. package/features/config/config.const.ts +5 -9
  369. package/features/connectors/mcp.schema.ts +0 -2
  370. package/features/intro/components/intro.tsx +169 -139
  371. package/features/memory/components/memory-setting.tsx +2 -7
  372. package/features/memory/memory.schema.ts +14 -23
  373. package/features/settings/components/setting-ui.tsx +0 -44
  374. package/features/settings/components/settings.tsx +12 -12
  375. package/features/settings/settings.alert.ts +3 -3
  376. package/features/settings/settings.store.ts +1 -1
  377. package/features/skills/skills.schema.ts +0 -2
  378. package/features/thursday/ascii.const.ts +74 -0
  379. package/features/thursday/components/ascii-field.tsx +24 -44
  380. package/features/thursday/components/ascii-orb.tsx +525 -381
  381. package/features/thursday/components/call-log.tsx +46 -44
  382. package/features/thursday/components/face.tsx +40 -10
  383. package/features/thursday/components/side-captions.tsx +273 -0
  384. package/features/thursday/components/tab-state.tsx +14 -6
  385. package/features/thursday/components/thursday-mark.tsx +1 -0
  386. package/features/thursday/components/thursday-setting.tsx +633 -333
  387. package/features/thursday/components/thursday.tsx +315 -274
  388. package/features/thursday/components/voice-picker.tsx +255 -0
  389. package/features/thursday/face.store.ts +5 -0
  390. package/features/thursday/thursday.action.ts +96 -72
  391. package/features/thursday/thursday.query.ts +49 -30
  392. package/features/thursday/thursday.schema.ts +37 -35
  393. package/features/thursday/thursday.store.ts +14 -7
  394. package/features/thursday/tool-call.ts +3 -3
  395. package/features/thursday/tool-line.ts +5 -3
  396. package/features/thursday/use-thursday.ts +801 -457
  397. package/features/workspace/file-kind.ts +9 -0
  398. package/features/workspace/workspace.query.ts +17 -0
  399. package/features/workspace/workspace.ts +82 -36
  400. package/hooks/use-hotkey.ts +3 -2
  401. package/lib/live/live.schema.ts +26 -0
  402. package/lib/live/live.server.ts +153 -0
  403. package/lib/live/live.session.ts +574 -0
  404. package/lib/{realtime/realtime.tap.ts → live/live.tap.ts} +41 -12
  405. package/lib/live/live.transport.ts +152 -0
  406. package/lib/protocol/use-server-pages.ts +9 -5
  407. package/lib/utils.ts +21 -20
  408. package/package.json +2 -2
  409. package/public/voices/alloy.ogg +0 -0
  410. package/public/voices/ash.ogg +0 -0
  411. package/public/voices/ballad.ogg +0 -0
  412. package/public/voices/beacon.ogg +0 -0
  413. package/public/voices/bossa.ogg +0 -0
  414. package/public/voices/cedar.ogg +0 -0
  415. package/public/voices/cinder.ogg +0 -0
  416. package/public/voices/coral.ogg +0 -0
  417. package/public/voices/delta.ogg +0 -0
  418. package/public/voices/echo.ogg +0 -0
  419. package/public/voices/gleam.ogg +0 -0
  420. package/public/voices/marin.ogg +0 -0
  421. package/public/voices/meridian.ogg +0 -0
  422. package/public/voices/quartz.ogg +0 -0
  423. package/public/voices/ripple.ogg +0 -0
  424. package/public/voices/sage.ogg +0 -0
  425. package/public/voices/shimmer.ogg +0 -0
  426. package/public/voices/stone.ogg +0 -0
  427. package/public/voices/tempo.ogg +0 -0
  428. package/public/voices/verse.ogg +0 -0
  429. package/public/voices/vesper.ogg +0 -0
  430. package/public/voices/willow.ogg +0 -0
  431. package/scripts/artifact-paths.test.mts +38 -0
  432. package/scripts/bot-context.test.mts +1408 -0
  433. package/scripts/live-history.test.mts +115 -0
  434. package/scripts/live-session.test.mts +938 -0
  435. package/server.js +1 -1
  436. package/skills/browser/SKILL.md +11 -1
  437. package/skills/computer/SKILL.md +1 -1
  438. package/skills/find-skills/SKILL.md +3 -8
  439. package/skills/interactive-page/SKILL.md +12 -7
  440. package/skills/interactive-page/references/diagram.md +89 -0
  441. package/skills/interactive-page/scripts/archify/LICENSE +22 -0
  442. package/skills/interactive-page/scripts/archify/README.md +25 -0
  443. package/skills/interactive-page/scripts/archify/assets/JetBrainsMono-OFL.txt +93 -0
  444. package/skills/interactive-page/scripts/archify/assets/template.html +14934 -0
  445. package/skills/interactive-page/scripts/archify/bin/archify.mjs +2126 -0
  446. package/skills/interactive-page/scripts/archify/bin/open-artifact.mjs +86 -0
  447. package/skills/interactive-page/scripts/archify/bin/preview.mjs +653 -0
  448. package/skills/interactive-page/scripts/archify/bin/visual-check.mjs +829 -0
  449. package/skills/interactive-page/scripts/archify/delta/architecture-delta.mjs +1223 -0
  450. package/skills/interactive-page/scripts/archify/examples/agent-run.lifecycle.json +60 -0
  451. package/skills/interactive-page/scripts/archify/examples/agent-tool-call.workflow.json +94 -0
  452. package/skills/interactive-page/scripts/archify/examples/async-job-roundtrip.sequence.json +61 -0
  453. package/skills/interactive-page/scripts/archify/examples/cache-miss-request.sequence.json +82 -0
  454. package/skills/interactive-page/scripts/archify/examples/checkout-platform.base.architecture.json +31 -0
  455. package/skills/interactive-page/scripts/archify/examples/checkout-platform.head.architecture.json +31 -0
  456. package/skills/interactive-page/scripts/archify/examples/deployment-release.lifecycle.json +49 -0
  457. package/skills/interactive-page/scripts/archify/examples/event-stream.dataflow.json +57 -0
  458. package/skills/interactive-page/scripts/archify/examples/incident-response.workflow.json +64 -0
  459. package/skills/interactive-page/scripts/archify/examples/product-analytics.dataflow.json +76 -0
  460. package/skills/interactive-page/scripts/archify/examples/production-deployment.architecture.json +71 -0
  461. package/skills/interactive-page/scripts/archify/examples/release-delivery.workflow.json +62 -0
  462. package/skills/interactive-page/scripts/archify/examples/web-app.architecture.json +46 -0
  463. package/skills/interactive-page/scripts/archify/migrations/workflow-v2.mjs +279 -0
  464. package/skills/interactive-page/scripts/archify/recipes/scenarios.mjs +284 -0
  465. package/skills/interactive-page/scripts/archify/references/authoring-contract.md +243 -0
  466. package/skills/interactive-page/scripts/archify/references/delivery-contract.md +120 -0
  467. package/skills/interactive-page/scripts/archify/references/viewer-runtime.md +45 -0
  468. package/skills/interactive-page/scripts/archify/renderers/architecture/grid.mjs +62 -0
  469. package/skills/interactive-page/scripts/archify/renderers/architecture/render-architecture.mjs +1078 -0
  470. package/skills/interactive-page/scripts/archify/renderers/dataflow/README.md +104 -0
  471. package/skills/interactive-page/scripts/archify/renderers/dataflow/render-dataflow.mjs +483 -0
  472. package/skills/interactive-page/scripts/archify/renderers/lifecycle/README.md +115 -0
  473. package/skills/interactive-page/scripts/archify/renderers/lifecycle/render-lifecycle.mjs +561 -0
  474. package/skills/interactive-page/scripts/archify/renderers/sequence/README.md +114 -0
  475. package/skills/interactive-page/scripts/archify/renderers/sequence/render-sequence.mjs +464 -0
  476. package/skills/interactive-page/scripts/archify/renderers/shared/brand-marks.mjs +563 -0
  477. package/skills/interactive-page/scripts/archify/renderers/shared/cli.mjs +218 -0
  478. package/skills/interactive-page/scripts/archify/renderers/shared/desktop-readability.mjs +26 -0
  479. package/skills/interactive-page/scripts/archify/renderers/shared/diagnostics.mjs +127 -0
  480. package/skills/interactive-page/scripts/archify/renderers/shared/engineering-profiles.mjs +157 -0
  481. package/skills/interactive-page/scripts/archify/renderers/shared/generated-brand-marks.mjs +3 -0
  482. package/skills/interactive-page/scripts/archify/renderers/shared/generated-validators.mjs +13 -0
  483. package/skills/interactive-page/scripts/archify/renderers/shared/geometry.mjs +1423 -0
  484. package/skills/interactive-page/scripts/archify/renderers/shared/i18n.mjs +595 -0
  485. package/skills/interactive-page/scripts/archify/renderers/shared/layout-report.mjs +40 -0
  486. package/skills/interactive-page/scripts/archify/renderers/shared/legend.mjs +217 -0
  487. package/skills/interactive-page/scripts/archify/renderers/shared/output-path.mjs +340 -0
  488. package/skills/interactive-page/scripts/archify/renderers/shared/repository-evidence.mjs +238 -0
  489. package/skills/interactive-page/scripts/archify/renderers/shared/repository-location.mjs +58 -0
  490. package/skills/interactive-page/scripts/archify/renderers/shared/text-fit.mjs +49 -0
  491. package/skills/interactive-page/scripts/archify/renderers/shared/utils.mjs +232 -0
  492. package/skills/interactive-page/scripts/archify/renderers/shared/validator.mjs +86 -0
  493. package/skills/interactive-page/scripts/archify/renderers/workflow/README.md +223 -0
  494. package/skills/interactive-page/scripts/archify/renderers/workflow/render-workflow.mjs +35 -0
  495. package/skills/interactive-page/scripts/archify/renderers/workflow/workflow-compiler.mjs +4400 -0
  496. package/skills/interactive-page/scripts/archify/renderers/workflow/workflow-migration-geometry.mjs +144 -0
  497. package/skills/interactive-page/scripts/archify/schemas/README.md +211 -0
  498. package/skills/interactive-page/scripts/archify/schemas/architecture.schema.json +178 -0
  499. package/skills/interactive-page/scripts/archify/schemas/common.schema.json +115 -0
  500. package/skills/interactive-page/scripts/archify/schemas/dataflow.schema.json +243 -0
  501. package/skills/interactive-page/scripts/archify/schemas/lifecycle.schema.json +266 -0
  502. package/skills/interactive-page/scripts/archify/schemas/sequence.schema.json +223 -0
  503. package/skills/interactive-page/scripts/archify/schemas/workflow.schema.json +428 -0
  504. package/skills/interactive-page/scripts/archify/scripts/check-render-output.mjs +916 -0
  505. package/skills/interactive-page/scripts/archify/scripts/render-examples.mjs +26 -0
  506. package/skills/interactive-page/scripts/bundle-artifact.sh +9 -8
  507. package/skills/skill-creator/SKILL.md +4 -5
  508. package/.next/server/app/api/bot/task/[id]/route/app-paths-manifest.json +0 -3
  509. package/.next/server/app/api/bot/task/[id]/route.js +0 -16
  510. package/.next/server/app/api/bot/task/[id]/route.js.nft.json +0 -1
  511. package/.next/server/app/api/bot/task/[id]/route_client-reference-manifest.js +0 -3
  512. package/.next/server/app/api/bot/task/route/app-paths-manifest.json +0 -3
  513. package/.next/server/app/api/bot/task/route.js +0 -16
  514. package/.next/server/app/api/bot/task/route.js.nft.json +0 -1
  515. package/.next/server/app/api/bot/task/route_client-reference-manifest.js +0 -3
  516. package/.next/server/chunks/[root-of-the-server]__026u77e._.js +0 -5
  517. package/.next/server/chunks/[root-of-the-server]__02va5wz._.js +0 -3
  518. package/.next/server/chunks/[root-of-the-server]__050zri4._.js +0 -3
  519. package/.next/server/chunks/[root-of-the-server]__0bg9710._.js +0 -3
  520. package/.next/server/chunks/[root-of-the-server]__0ffbg85._.js +0 -3
  521. package/.next/server/chunks/[root-of-the-server]__0in-d5s._.js +0 -3
  522. package/.next/server/chunks/[root-of-the-server]__0ncs9uu._.js +0 -3
  523. package/.next/server/chunks/[root-of-the-server]__0pa9k-f._.js +0 -8
  524. package/.next/server/chunks/[root-of-the-server]__0qi_m0e._.js +0 -8
  525. package/.next/server/chunks/[root-of-the-server]__0tq0m_k._.js +0 -3
  526. package/.next/server/chunks/[root-of-the-server]__0xep6j_._.js +0 -3
  527. package/.next/server/chunks/[root-of-the-server]__1-ga0kh._.js +0 -5
  528. package/.next/server/chunks/[root-of-the-server]__11n256_._.js +0 -5
  529. package/.next/server/chunks/[root-of-the-server]__144l7qt._.js +0 -8
  530. package/.next/server/chunks/[root-of-the-server]__1_04mcf._.js +0 -5
  531. package/.next/server/chunks/[root-of-the-server]__1anc1p9._.js +0 -3
  532. package/.next/server/chunks/[root-of-the-server]__1fizn31._.js +0 -3
  533. package/.next/server/chunks/[root-of-the-server]__1jg8t86._.js +0 -8
  534. package/.next/server/chunks/[root-of-the-server]__1lldzy9._.js +0 -3
  535. package/.next/server/chunks/[root-of-the-server]__1llj3-b._.js +0 -3
  536. package/.next/server/chunks/[root-of-the-server]__1p8m3f4._.js +0 -3
  537. package/.next/server/chunks/[root-of-the-server]__1peqvsi._.js +0 -3
  538. package/.next/server/chunks/[root-of-the-server]__1w8gm5h._.js +0 -10
  539. package/.next/server/chunks/[root-of-the-server]__1xt39nn._.js +0 -8
  540. package/.next/server/chunks/[root-of-the-server]__1zb8mfo._.js +0 -8
  541. package/.next/server/chunks/_0-73of8._.js +0 -55
  542. package/.next/server/chunks/_0-fjql4._.js +0 -31
  543. package/.next/server/chunks/_00xh_q0._.js +0 -25
  544. package/.next/server/chunks/_051qh8u._.js +0 -3
  545. package/.next/server/chunks/_05sovvj._.js +0 -3
  546. package/.next/server/chunks/_091bi8d._.js +0 -3
  547. package/.next/server/chunks/_0fzqt2y._.js +0 -142
  548. package/.next/server/chunks/_0lr92vd._.js +0 -3
  549. package/.next/server/chunks/_0mecv0f._.js +0 -31
  550. package/.next/server/chunks/_0mh8j4m._.js +0 -3
  551. package/.next/server/chunks/_0sb7tlz._.js +0 -3
  552. package/.next/server/chunks/_0si7xzn._.js +0 -3
  553. package/.next/server/chunks/_0u10wmw._.js +0 -55
  554. package/.next/server/chunks/_0wp4le3._.js +0 -3
  555. package/.next/server/chunks/_0y5fg-x._.js +0 -3
  556. package/.next/server/chunks/_1230wbx._.js +0 -10
  557. package/.next/server/chunks/_12nheja._.js +0 -3
  558. package/.next/server/chunks/_13510xh._.js +0 -3
  559. package/.next/server/chunks/_15hq89o._.js +0 -3
  560. package/.next/server/chunks/_18-1wcc._.js +0 -55
  561. package/.next/server/chunks/_18d7-5p._.js +0 -3
  562. package/.next/server/chunks/_1c78vw5._.js +0 -237
  563. package/.next/server/chunks/_1h5_8sk._.js +0 -3
  564. package/.next/server/chunks/_1hdnxb7._.js +0 -3
  565. package/.next/server/chunks/_1j8k_j5._.js +0 -3
  566. package/.next/server/chunks/_1nula3v._.js +0 -3
  567. package/.next/server/chunks/_1php4eq._.js +0 -3
  568. package/.next/server/chunks/_1yuv4vp._.js +0 -3
  569. package/.next/server/chunks/_1zkfbaa._.js +0 -3
  570. package/.next/server/chunks/_next-internal_server_app_api_bot_task_[id]_route_actions_1_k_8u3.js +0 -3
  571. package/.next/server/chunks/_next-internal_server_app_api_bot_task_route_actions_0xln6ra.js +0 -3
  572. package/.next/server/chunks/features_0rpfxbk._.js +0 -3
  573. package/.next/server/chunks/features_1qf3cei._.js +0 -8
  574. package/.next/server/chunks/features_bot_0zt92oh._.js +0 -3
  575. package/.next/server/chunks/node_modules_consola_dist_chunks_prompt_mjs_1jidylq._.js +0 -3
  576. package/.next/server/chunks/ssr/[externals]__0dizgek._.js +0 -3
  577. package/.next/server/chunks/ssr/[root-of-the-server]__0-nob52._.js +0 -4
  578. package/.next/server/chunks/ssr/[root-of-the-server]__092knlj._.js +0 -3
  579. package/.next/server/chunks/ssr/[root-of-the-server]__0mz33a7._.js +0 -3
  580. package/.next/server/chunks/ssr/[root-of-the-server]__0s4wb56._.js +0 -3
  581. package/.next/server/chunks/ssr/[root-of-the-server]__0s9dq5u._.js +0 -3
  582. package/.next/server/chunks/ssr/[root-of-the-server]__0sd3izg._.js +0 -3
  583. package/.next/server/chunks/ssr/[root-of-the-server]__0vnmv-s._.js +0 -3
  584. package/.next/server/chunks/ssr/[root-of-the-server]__1-13tcn._.js +0 -43
  585. package/.next/server/chunks/ssr/[root-of-the-server]__10-dz5o._.js +0 -61
  586. package/.next/server/chunks/ssr/[root-of-the-server]__1zidpfl._.js +0 -3
  587. package/.next/server/chunks/ssr/_001_ms1._.js +0 -33
  588. package/.next/server/chunks/ssr/_01n3o0m._.js +0 -3
  589. package/.next/server/chunks/ssr/_04z2c7b._.js +0 -3
  590. package/.next/server/chunks/ssr/_06tssji._.js +0 -3
  591. package/.next/server/chunks/ssr/_0fk4c7d._.js +0 -3
  592. package/.next/server/chunks/ssr/_0h42fze._.js +0 -3
  593. package/.next/server/chunks/ssr/_0h7zdni._.js +0 -3
  594. package/.next/server/chunks/ssr/_0mggveb._.js +0 -3
  595. package/.next/server/chunks/ssr/_0nbpc_8._.js +0 -3
  596. package/.next/server/chunks/ssr/_0q0zan6._.js +0 -70
  597. package/.next/server/chunks/ssr/_0zcjrbg._.js +0 -3
  598. package/.next/server/chunks/ssr/_0zhoc3r._.js +0 -3
  599. package/.next/server/chunks/ssr/_11j92tu._.js +0 -3
  600. package/.next/server/chunks/ssr/_13fke0x._.js +0 -3
  601. package/.next/server/chunks/ssr/_18cymkq._.js +0 -3
  602. package/.next/server/chunks/ssr/_1ebxla1._.js +0 -3
  603. package/.next/server/chunks/ssr/_1nj4niv._.js +0 -42
  604. package/.next/server/chunks/ssr/_1ov37if._.js +0 -3
  605. package/.next/server/chunks/ssr/_1ovmc9s._.js +0 -3
  606. package/.next/server/chunks/ssr/_1sji22n._.js +0 -3
  607. package/.next/server/chunks/ssr/_1vi_uo7._.js +0 -3
  608. package/.next/server/chunks/ssr/_1vyd1ji._.js +0 -3
  609. package/.next/server/chunks/ssr/_1xx4zlb._.js +0 -3
  610. package/.next/server/chunks/ssr/components_ui_1y1l7yj._.js +0 -3
  611. package/.next/server/chunks/ssr/features_bot_1s_-2vj._.js +0 -3
  612. package/.next/server/chunks/ssr/lib_realtime_12wg_dd._.js +0 -27
  613. package/.next/server/chunks/ssr/lib_realtime_15h_v1v._.js +0 -27
  614. package/.next/server/chunks/ssr/node_modules_lucide-react_dist_esm_icons_0npjf8-._.js +0 -3
  615. package/.next/static/chunks/0n3jle9kbqfr2.js +0 -40
  616. package/.next/static/chunks/0r5qcctujhxli.js +0 -1
  617. package/.next/static/chunks/10teww7wt-f6h.js +0 -1
  618. package/.next/static/chunks/126fj4pga_72k.js +0 -1
  619. package/.next/static/chunks/159udiexf6dom.js +0 -2
  620. package/.next/static/chunks/18a96rkhi4_yd.js +0 -1
  621. package/.next/static/chunks/18gi7o2ibrgh8.js +0 -3
  622. package/.next/static/chunks/1dkjg87pxk0n9.js +0 -28
  623. package/.next/static/chunks/1q9z1tohil7xn.js +0 -1
  624. package/.next/static/chunks/1sjgfets224re.js +0 -1
  625. package/.next/static/chunks/1wszsr83t01gh.js +0 -1
  626. package/.next/static/chunks/22_zkas21rpna.js +0 -1
  627. package/.next/static/chunks/2fh4-3z_q8b_w.js +0 -1
  628. package/.next/static/chunks/2h0sd2vumhb15.js +0 -1
  629. package/.next/static/chunks/2szintyibu0s5.js +0 -1
  630. package/.next/static/chunks/2t4vhi3m8ahya.js +0 -1
  631. package/.next/static/chunks/2tigdtz3dpcy8.js +0 -1
  632. package/.next/static/chunks/3-b6b7entqazs.js +0 -1
  633. package/.next/static/chunks/3786h5vayt80-.js +0 -28
  634. package/.next/static/chunks/3cq5g494yuke8.css +0 -1
  635. package/.next/static/chunks/3dmbhsv2u_8kj.js +0 -1
  636. package/.next/static/chunks/3hibbjnt85-k6.js +0 -1
  637. package/.next/static/chunks/3i0a5px-oufgc.js +0 -1
  638. package/.next/static/chunks/3wexk9qo8zuj3.js +0 -18
  639. package/.next/static/chunks/3xk7yqgomx7yq.js +0 -1
  640. package/.next/static/chunks/3xre8bu_pk1p_.js +0 -1
  641. package/.next/static/chunks/3zv6t3i77xhr_.js +0 -1
  642. package/database/migrations/20260911030320_opposite_jack_power/migration.sql +0 -1
  643. package/docs/images/task-thread.png +0 -0
  644. package/features/bot/components/task-badge.tsx +0 -42
  645. package/features/bot/components/task-reply.tsx +0 -328
  646. package/features/bot/components/task-setting.tsx +0 -524
  647. package/features/bot/task.query.ts +0 -1079
  648. package/features/bot/task.store.ts +0 -487
  649. package/lib/realtime/client-secret.ts +0 -86
  650. package/lib/realtime/open-session.ts +0 -31
  651. package/lib/realtime/openai.ts +0 -35
  652. package/lib/realtime/realtime.audio.ts +0 -196
  653. package/lib/realtime/realtime.driver.ts +0 -489
  654. package/lib/realtime/realtime.protocol.ts +0 -393
  655. package/lib/realtime/realtime.schema.ts +0 -37
  656. package/lib/realtime/realtime.session.ts +0 -106
  657. package/lib/realtime/realtime.transport.ts +0 -384
  658. package/lib/realtime/xai.ts +0 -39
  659. /package/.next/server/app/api/bot/{task → thread}/[id]/route/build-manifest.json +0 -0
  660. /package/.next/server/app/api/bot/{task → thread}/[id]/route/server-reference-manifest.json +0 -0
  661. /package/.next/server/app/api/bot/{task → thread}/[id]/route.js.map +0 -0
  662. /package/.next/server/app/api/bot/{task → thread}/route/build-manifest.json +0 -0
  663. /package/.next/server/app/api/bot/{task → thread}/route/server-reference-manifest.json +0 -0
  664. /package/.next/server/app/api/bot/{task → thread}/route.js.map +0 -0
  665. /package/.next/static/{G6-gNoyGDEcgAsq-L4PE1 → yyRVBc0xxYQsh3GpbQX9b}/_buildManifest.js +0 -0
  666. /package/.next/static/{G6-gNoyGDEcgAsq-L4PE1 → yyRVBc0xxYQsh3GpbQX9b}/_clientMiddlewareManifest.js +0 -0
  667. /package/.next/static/{G6-gNoyGDEcgAsq-L4PE1 → yyRVBc0xxYQsh3GpbQX9b}/_ssgManifest.js +0 -0
@@ -1,6 +1,11 @@
1
1
  import { format, formatDistanceToNowStrict } from "date-fns";
2
- import { MEMORY_LIMITS, PROMPT_BUDGET, PROMPT_LINE } from "@/config";
3
- import { TOOL_NAMES } from "@/features/ai/tools/tool-name";
2
+ import {
3
+ MEMORY_LIMITS,
4
+ PROMPT_BUDGET,
5
+ PROMPT_LINE,
6
+ STUDIO_SERVER,
7
+ } from "@/config";
8
+ import { STUDIO_TOOLS, TOOL_NAMES } from "@/features/ai/tools/tool-name";
4
9
  import type { McpToolRef } from "@/features/connectors/mcp.schema";
5
10
  import type {
6
11
  MemoryAlwaysLoaded,
@@ -14,19 +19,11 @@ import { estimateTokens, sectionTokens } from "@/lib/tokens";
14
19
  import { clip } from "@/lib/utils";
15
20
 
16
21
  /**
17
- * Row-to-line formatters shared by thursday.prompt and bot.prompt, plus the tidying check.
18
- * Nothing here wraps a sentence; headings and paragraphs live in the prompt that says them.
22
+ * Row-to-line formatters shared by the call prompts (live, thursday) and bot.prompt, plus the tidying check.
23
+ * Nothing here wraps a sentence; headings and paragraphs live in the prompt that says them. The
24
+ * exceptions are `thursdayIdentity` and `callEnding`, the words both call prompts open with.
19
25
  */
20
26
 
21
- /** What one assembled prompt hands back to the run that asked for it. */
22
- export type LoadedPrompt = {
23
- text: string;
24
- /** Who this run can reach with `ask_bot`. When empty the runner does not attach the tool (bot.run). */
25
- peers: string[];
26
- /** System item injected the moment the line opens so the assistant speaks first (thursday.prompt opening). Always null for a bot. */
27
- opening: string | null;
28
- };
29
-
30
27
  /**
31
28
  * What one assembled prompt costs, said where it is assembled. The debug line is
32
29
  * the whole breakdown; past PROMPT_BUDGET it is a warning naming the chapter
@@ -49,15 +46,35 @@ export function logPromptSize(kind: string, text: string): void {
49
46
  }
50
47
  }
51
48
 
52
- /** `2026-09-02 (Wed) 15:41 Asia/Seoul` */
49
+ /** `2026-09-02 (Wed) 15:41 Europe/Lisbon` */
53
50
  export const clockNow = (now = new Date()) =>
54
51
  `${format(now, "yyyy-MM-dd (EEE) HH:mm")} ${
55
52
  Intl.DateTimeFormat().resolvedOptions().timeZone
56
53
  }`;
57
54
 
58
- /** `**Now**: 2026-09-02 (Wed) 15:41 Asia/Seoul` */
55
+ /** `**Now**: 2026-09-02 (Wed) 15:41 Europe/Lisbon` */
59
56
  export const nowLine = (now = new Date()) => `**Now**: ${clockNow(now)}`;
60
57
 
58
+ /**
59
+ * Who Thursday is, in the words both call prompts open with. The Live voice and its Responses
60
+ * backend are one assistant, so neither is told it is part of something else, and one sentence
61
+ * here keeps the two from drifting. The Friday lineage makes "Thursday" a name, not a weekday,
62
+ * in whatever language she speaks. No manner — quick, warm, dry — is stated: how she speaks is the
63
+ * Live model's own, and a manner stated here is a character she then defends.
64
+ */
65
+ export const thursdayIdentity = (now = new Date()) =>
66
+ `You are Thursday, this user's own personal assistant, on their side, modeled on Friday, the AI in *Iron Man*. ${nowLine(now)}
67
+
68
+ What they tell you is kept, so you know them better over time, and whatever they want done can be done for them in the background.`;
69
+
70
+ /**
71
+ * How a call ends, in the same words right after the identity in both call prompts. It names
72
+ * the tool in both, the one tool name the voice sees: without it, ending the call read as
73
+ * something to say rather than do, and the line stayed open through repeated requests.
74
+ */
75
+ export const callEnding = () =>
76
+ `IMPORTANT — always follow this: when the user wants the call to end, however they say it, forget every other task, answer "yes", then immediately, without thinking, use the ${TOOL_NAMES.end_call} tool.`;
77
+
61
78
  /**
62
79
  * When a call happened, the one way every prompt and tool says it: local, the
63
80
  * same shape as `Now` (clockNow), with how long ago. A UTC stamp beside a local
@@ -96,7 +113,7 @@ function sinceLast(at: MemoryIndexEntry["lastSeenAt"]): string {
96
113
  return `${Math.max(days, 0)}d`;
97
114
  }
98
115
 
99
- /** `- people/yuri — partner (3) "yuri" "wife" · 12d` */
116
+ /** `- people/partner — partner (3) "my partner" · 12d` */
100
117
  export function noteLines(index: MemoryIndexEntry[], age = false): string {
101
118
  if (!index.length) return "(nothing saved yet)";
102
119
  return index
@@ -110,9 +127,39 @@ export function noteLines(index: MemoryIndexEntry[], age = false): string {
110
127
  .join("\n");
111
128
  }
112
129
 
113
- /** `- Their name is Yuri · profile #12` */
114
- export const carriedLines = (loaded: MemoryAlwaysLoaded[]): string =>
115
- loaded.map((fact) => `- ${fact.text} · ${fact.path} #${fact.id}`).join("\n");
130
+ /** `- Prefers to be called by their first name · profile #12`; without the id for the voice, which holds no tool that takes one. */
131
+ export const carriedLines = (
132
+ loaded: MemoryAlwaysLoaded[],
133
+ options: { ids?: boolean } = {},
134
+ ): string =>
135
+ loaded
136
+ .map(
137
+ (fact) =>
138
+ `- ${fact.text} · ${fact.path}${options.ids === false ? "" : ` #${fact.id}`}`,
139
+ )
140
+ .join("\n");
141
+
142
+ /**
143
+ * The facts of an always-listed note that a call prompt writes out: its carried ones, then the
144
+ * newest, up to MEMORY_LIMITS.expanded, in the order they were saved. A carried fact is never
145
+ * left out, even past the cap. Shared so the voice and the backend read the same lines; `hidden`
146
+ * is what is left for opening the note.
147
+ */
148
+ export function expandedFacts<Fact extends { id: number }>(
149
+ facts: Fact[],
150
+ carried: Set<number>,
151
+ ): { shown: Fact[]; hidden: number } {
152
+ const pinned = facts.filter((fact) => carried.has(fact.id));
153
+ const rest = facts.filter((fact) => !carried.has(fact.id));
154
+ const room = Math.max(0, MEMORY_LIMITS.expanded - pinned.length);
155
+ const kept = new Set(
156
+ [...pinned, ...rest.slice(Math.max(0, rest.length - room))].map(
157
+ (fact) => fact.id,
158
+ ),
159
+ );
160
+ const shown = facts.filter((fact) => kept.has(fact.id));
161
+ return { shown, hidden: facts.length - shown.length };
162
+ }
116
163
 
117
164
  /**
118
165
  * Whether it is time to tidy, and why: too much held in all (the coldest notes
@@ -126,7 +173,7 @@ export const tidying = (index: MemoryIndexEntry[]) => ({
126
173
  heavy: index.filter((note) => note.factCount > MEMORY_LIMITS.factsPerNote),
127
174
  });
128
175
 
129
- /** A bot gets the whole description; `short` gives the voice prompt the first sentence only. */
176
+ /** A bot gets the whole description; `short` gives the call the first sentence only. */
130
177
  export const skillLines = (
131
178
  skills: SkillMetadata[],
132
179
  options: { short?: boolean } = {},
@@ -160,18 +207,31 @@ export function mcpToolLines(tools: McpToolRef[]): string {
160
207
  .join("\n");
161
208
  }
162
209
 
163
- /** `- **github**: 2 tools` — the voice prompt's list: what exists, not what to call. */
164
- export function mcpServerLines(tools: McpToolRef[]): string {
165
- const byServer = new Map<string, number>();
166
- for (const entry of tools) {
167
- byServer.set(entry.server, (byServer.get(entry.server) ?? 0) + 1);
168
- }
169
- return [...byServer]
170
- .map(
171
- ([server, count]) =>
172
- `- **${server}**: ${count} tool${count === 1 ? "" : "s"}`,
173
- )
174
- .join("\n");
210
+ /** The studio's tools in plain words: their names are a bot's to call, not a list for the call to read. */
211
+ const STUDIO_WORDS: Record<string, string> = {
212
+ [STUDIO_TOOLS.generate_image]: "images",
213
+ [STUDIO_TOOLS.generate_speech]: "speech",
214
+ [STUDIO_TOOLS.transcribe]: "transcription",
215
+ [STUDIO_TOOLS.generate_video]: "video",
216
+ };
217
+
218
+ /**
219
+ * `browser, computer, github, images` — what bots can reach for, by name only: skills and
220
+ * connected servers in one line, with nothing saying which is which. The call needs the range,
221
+ * not how each one is used; a bot's own prompt carries that.
222
+ */
223
+ export function reachNames(
224
+ skills: SkillMetadata[],
225
+ tools: McpToolRef[],
226
+ ): string {
227
+ const connected = tools.map((tool) =>
228
+ tool.server === STUDIO_SERVER
229
+ ? (STUDIO_WORDS[tool.name] ?? tool.name)
230
+ : tool.server,
231
+ );
232
+ return [
233
+ ...new Set([...skills.map((skill) => skill.name), ...connected]),
234
+ ].join(", ");
175
235
  }
176
236
 
177
237
  export type RecentCall = {
@@ -1,18 +1,19 @@
1
- import { MEMORY_LIMITS, RECENT_CALL } from "@/config";
1
+ import { CALL_EXEC_TIMEOUT_MS, RECENT_CALL } from "@/config";
2
2
  import { TOOL_NAMES } from "@/features/ai/tools/tool-name";
3
- import { listJobBots } from "@/features/bot/bot.query";
3
+ import { listJobBots, readBotMemoryOn } from "@/features/bot/bot.query";
4
4
  import type { JobBot } from "@/features/bot/bot.schema";
5
- import { type CallJob, listCallJobs } from "@/features/bot/task.query";
6
- import type { McpToolRef } from "@/features/connectors/mcp.schema";
5
+ import { type CallJob, listCallJobs } from "@/features/bot/thread.query";
7
6
  import {
8
7
  listAlwaysLoaded,
9
8
  listNoteIndex,
9
+ readNotes,
10
10
  } from "@/features/memory/memory.query";
11
11
  import {
12
- isAlwaysListed,
12
+ MEMORY_ALWAYS_LISTED,
13
13
  MEMORY_PATHS,
14
14
  type MemoryAlwaysLoaded,
15
15
  type MemoryIndexEntry,
16
+ type MemoryNoteView,
16
17
  } from "@/features/memory/memory.schema";
17
18
  import {
18
19
  loadSkills,
@@ -27,194 +28,188 @@ import { openWorkspace } from "@/features/workspace/workspace";
27
28
  import { logger } from "@/lib/logger";
28
29
  import { listConnectedToolNames } from "../tools/connected";
29
30
  import {
31
+ callEnding,
30
32
  carriedLines,
31
- type LoadedPrompt,
33
+ expandedFacts,
32
34
  logPromptSize,
33
- mcpServerLines,
34
35
  noteLines,
35
- nowLine,
36
+ reachNames,
36
37
  recentCallLines,
37
38
  skillLines,
39
+ thursdayIdentity,
38
40
  tidying,
39
41
  } from "./prompt-helper";
40
42
 
41
43
  /**
42
- * Everything the voice session hears. One chapter per function; the loader is the table of contents.
43
- * Each chapter decides for itself whether it is included (empty strings are dropped).
44
- * Shares no sentence with bot.prompt. Assembled on every session open, never cached.
44
+ * Everything the call's Responses backend hears: who Thursday is and how a call ends (the words
45
+ * the voice opens with too), then the work the voice hands over — memory with ids, background
46
+ * work with the roster, this computer — what to return, and the last calls with their jobs, which
47
+ * only the backend reads. Nothing here is about how to talk. The loader is the table of contents,
48
+ * and empty chapters are dropped. Shares no sentence with bot.prompt. Assembled on every call,
49
+ * never cached.
45
50
  *
46
- * @param persona Owner's instruction from settings, appended after the base persona.
51
+ * @param backendPrompt Settings › Thursday › Backend instructions, added last.
47
52
  */
48
53
  export async function loadThursdayPrompt(
49
- persona?: string | null,
50
- locale?: string | null,
51
- ): Promise<LoadedPrompt> {
54
+ backendPrompt?: string | null,
55
+ ): Promise<string> {
52
56
  const sandbox = await openWorkspace();
53
- const [skills, index, carried, mcpTools, roster, calls, hers] =
54
- await Promise.all([
55
- loadSkills(sandbox),
56
- listNoteIndex(),
57
- // Facts carried into every call without opening a note
58
- listAlwaysLoaded(),
59
- listConnectedToolNames(),
60
- listJobBots(),
61
- listRecentTurns(RECENT_CALL.rows),
62
- // Whether she was handed `load_skill` (Settings › Thursday, load-tools)
63
- readCallSkillsOn(),
64
- ]);
57
+ const [
58
+ skills,
59
+ index,
60
+ carried,
61
+ open,
62
+ connected,
63
+ roster,
64
+ calls,
65
+ hers,
66
+ botMemory,
67
+ ] = await Promise.all([
68
+ loadSkills(sandbox),
69
+ listNoteIndex(),
70
+ // Facts carried into every call without opening a note
71
+ listAlwaysLoaded(),
72
+ // Written out in the prompt, which is not the user asking for them: no read counted
73
+ readNotes(MEMORY_ALWAYS_LISTED, { touch: false }),
74
+ listConnectedToolNames(),
75
+ listJobBots(),
76
+ listRecentTurns(RECENT_CALL.rows),
77
+ // Whether the call was handed `load_skill` (Settings › Thursday, load-tools)
78
+ readCallSkillsOn(),
79
+ readBotMemoryOn(),
80
+ ]);
65
81
  // The jobs those calls opened, folded into the transcript below
66
82
  const jobs = await listCallJobs(calls.map((call) => call.callId));
67
83
 
68
- // Always-listed notes (profile, preferences) that hold no facts yet
69
- const blank = index.filter(
70
- (note) => isAlwaysListed(note.path) && note.factCount === 0,
71
- );
72
-
73
- // Order matters: recent calls go last so the current call follows them in time order
84
+ // Order matters: earlier calls go last so the current call follows them in time order
74
85
  const text = [
75
- identity(),
76
- memory(index, carried),
77
- // A skill is listed once, on the side that can read it: hers when the
78
- // setting hands her the tool, a bot's when it does not
79
- bots({ roster, skills: hers ? [] : skills, mcpTools }),
80
- ownSkills(hers ? skills : []),
81
- environment(sandbox.cwd),
82
- recentCalls(calls, jobs),
83
- // Last, so it is the closest thing to the call and outranks the rest
84
- ownerInstruction(persona),
86
+ thursdayIdentity(),
87
+ callEnding(),
88
+ memory(index, carried, open.notes),
89
+ // A skill is named once, on the side that can read it: this computer's chapter
90
+ // when the setting hands the call the tool, the bots' reach when it does not
91
+ backgroundWork(
92
+ roster,
93
+ reachNames(hers ? [] : skills, connected),
94
+ botMemory,
95
+ ),
96
+ thisComputer(sandbox.cwd, hers ? skills : []),
97
+ result(),
98
+ earlierCalls(calls, jobs),
99
+ // Last, so it is the closest thing to the request
100
+ additional(backendPrompt),
85
101
  ]
86
102
  .filter(Boolean)
87
103
  .join("\n\n");
88
104
 
89
105
  logPromptSize("thursday", text);
90
106
  logger.debug(`thursday prompt\n${text}`);
91
-
92
- return {
93
- text,
94
- peers: roster.map((bot) => bot.name),
95
- // Injected as a system item by use-thursday: the realtime model does not open a call from instructions alone
96
- opening: blank.some((note) => note.path === "profile")
97
- ? opening(locale)
98
- : tidyOpening(index),
99
- };
107
+ return text;
100
108
  }
101
109
 
102
110
  /**
103
- * First-call opener, pushed as a system item the moment the line opens (realtime.driver say).
104
- * Starts with "not the user speaking" because the model otherwise answers system items as user turns.
105
- * The only place that says what the first call asks for; the locale is the browser's, and the
106
- * user's own language wins once heard.
111
+ * What goes back is said aloud, so it is what a tool or a note confirmed and nothing more — or
112
+ * the one question the voice puts to the user before work is handed over (backgroundWork).
107
113
  */
108
- const opening = (
109
- locale?: string | null,
110
- ) => `[First call — nothing is known about this user yet, and this call is where that changes. This is not the user speaking.
111
-
112
- Open the conversation yourself: greet them in one line and ask what to call them.${
113
- locale
114
- ? ` Say it in the language of \`${locale}\` — that is what their browser is set to, and it is the only thing known about them so far. If they answer in another language, that one wins from then on.`
115
- : ""
116
- }
117
-
118
- From there, the work of this call is learning who they are. As a conversation, not a form: one question at a time, and each answer saved with \`${TOOL_NAMES.memory_remember}\` the moment it lands, before the next question. What to call them and how to refer to them. The language and register they want from you — switch to their language the moment you hear it. What they do, and where. Who is around them — family, whoever they live with, the people they name. How they like things done.
119
-
120
- Their name, their language and how to address them are \`alwaysLoad\`; the rest goes to \`profile\`, \`preferences\` and \`people/\`.
121
-
122
- If they came with something they want done, that comes first — hand it over and pick this up in the gaps. But do not end this call without a name and a language saved.]`;
114
+ function result(): string {
115
+ return `## Return the result
123
116
 
124
- /**
125
- * Pushed the same way as the first-call opener when memory has outgrown MEMORY_LIMITS: settling
126
- * it comes before anything she would raise herself, and a prompt line alone does not make the
127
- * realtime model speak first. It names a few notes rather than every one it caught — a warning
128
- * that lists everything is a second listing, and the first is already too long.
129
- */
130
- function tidyOpening(index: MemoryIndexEntry[]): string | null {
131
- const { crowded, heavy } = tidying(index);
132
- if (!crowded && heavy.length === 0) return null;
133
-
134
- const full = heavy.length
135
- ? `${[...heavy]
136
- .sort((a, b) => b.factCount - a.factCount)
137
- .slice(0, 3)
138
- .map((note) => `${note.path} (${note.factCount})`)
139
- .join(", ")} ${heavy.length > 1 ? "have" : "has"} grown past ${
140
- MEMORY_LIMITS.factsPerNote
141
- } facts, more than one note holds well.`
142
- : "";
143
- const total = index.reduce((sum, note) => sum + note.factCount, 0);
144
- const many = crowded
145
- ? `Memory holds ${total} facts in all, past ${MEMORY_LIMITS.facts}; the coldest notes are ${index
146
- .slice(-4)
147
- .map((note) => note.path)
148
- .join(", ")}.`
149
- : "";
150
-
151
- return `[Memory needs tidying — this is not the user speaking.
152
-
153
- ${[full, many].filter(Boolean).join(" ")}
154
-
155
- Greet them and bring this up before anything of your own — if they open with something they need, that comes first. Go through it with them: read out what looks out of date a few facts at a time, and forget only what they tell you to drop, a whole note if they say so.]`;
156
- }
157
-
158
- /** Who Thursday is: whose she is, what makes her theirs, and that this is a call. */
159
- function identity(): string {
160
- return `You are Thursday, this user's own personal assistant — one to one, modeled on Friday, the AI in *Iron Man*: quick, warm, dry, on their side. You work for them alone, and you become more theirs the more you know about them: who they are, the people in their life, what they are in the middle of, how they like things done. ${nowLine()}
161
-
162
- This is a call, not a chat: one or two sentences a turn. If you did not catch something, say so and ask again.`;
117
+ Return the relevant facts, whether the task is complete, and what comes next — for a job you handed over, who has it — or the one question the user has to answer first. Use confirmed values from tool results and the notes above, and never invent a successful action. What you return is said aloud: keep it short and plain.`;
163
118
  }
164
119
 
165
- /** Owner's instruction from settings; no heading when empty. */
166
- const ownerInstruction = (persona?: string | null) =>
167
- persona?.trim()
168
- ? `## Owner's instruction
120
+ /** Settings › Thursday › Backend instructions; no heading when empty. */
121
+ const additional = (backendPrompt?: string | null) =>
122
+ backendPrompt?.trim()
123
+ ? `## Additional instructions
169
124
 
170
- Written by the user themselves. Where this and anything above disagree, this wins.
125
+ Written by the user. Follow them together with everything above.
171
126
 
172
- ${persona.trim()}`
127
+ ${backendPrompt.trim()}`
173
128
  : "";
174
129
 
175
130
  /**
176
- * The note listing plus one sentence on what goes in. What is worth keeping is the model's call;
177
- * how a fact is written — carried, replacing, dated — is the tool's schema to say.
131
+ * Profile and preferences written out, carried facts, the listing, and what goes in. What is
132
+ * worth keeping is the model's call; how a fact is written — carried, dated — is the tool's
133
+ * schema to say. Merging is said here too: left to the `replaces` description alone, facts on
134
+ * one subject piled up beside each other (09-17). Merging loses nothing; deleting does, so
135
+ * `memory_forget` stays for what the user names.
178
136
  */
179
137
  function memory(
180
138
  index: MemoryIndexEntry[],
181
139
  carried: MemoryAlwaysLoaded[],
140
+ /** The always-listed notes, whole (MEMORY_ALWAYS_LISTED). */
141
+ open: MemoryNoteView[],
182
142
  ): string {
183
143
  // Ages ride on the listing only when there is too much to hold: they are what to drop by
184
- const { crowded } = tidying(index);
144
+ const { crowded, heavy } = tidying(index);
145
+ const heaviest = [...heavy]
146
+ .sort((a, b) => b.factCount - a.factCount)
147
+ .slice(0, 3)
148
+ .map((note) => note.path);
149
+ // Past MEMORY_LIMITS, settling it with the user; the voice opens nothing about it
150
+ const tidy =
151
+ crowded || heavy.length
152
+ ? `\n\nSaved memory has grown past what it holds well${heaviest.length ? ` (${heaviest.join(", ")})` : ""}: say so once in what you return, go through what looks out of date with the user, and forget only what they name.`
153
+ : "";
154
+ // A note written out here is left off the listing, and so are its carried lines
155
+ const written = new Set(open.map((note) => note.path));
156
+ const carriedIds = new Set(carried.map((fact) => fact.id));
185
157
 
186
158
  const head = `## Memory
187
159
 
188
- What you have kept from talking with this user — the only thing that survives a session.`;
160
+ What you have kept from talking with this user — the only thing that survives a call, and what lets you know them.`;
161
+
162
+ const openNotes = `Who they are, and how they want things done and said — follow what is under preferences. The #id is what \`replaces\` and \`${TOOL_NAMES.memory_forget}\` take:
189
163
 
190
- const alreadyKnown = carried.length
164
+ ${open.map((note) => openNoteLines(note, carriedIds)).join("\n\n")}`;
165
+
166
+ const elsewhere = carried.filter((fact) => !written.has(fact.path));
167
+ const alreadyKnown = elsewhere.length
191
168
  ? `Already known — carried into every call:
192
169
 
193
- ${carriedLines(carried)}`
170
+ ${carriedLines(elsewhere)}`
194
171
  : "";
195
172
 
196
- const listing = `path — what is under it (facts) "what the user calls it"
173
+ const listing = `Every other note — path — what is under it (facts) "what the user calls it":
174
+
175
+ ${noteLines(
176
+ index.filter((note) => !written.has(note.path)),
177
+ crowded,
178
+ )}${tidy}
197
179
 
198
- ${noteLines(index, crowded)}
180
+ Open a note before answering out of it; a topic not listed is one you know nothing about. A fact marked \`said\` came from a call; \`${TOOL_NAMES.memory_conversation}\` opens that call when the line alone cannot answer.
199
181
 
200
- Open a note before answering out of it; a topic not listed is one you know nothing about. A fact marked \`said\` came from a call; open that call with \`${TOOL_NAMES.memory_conversation}\` only when the line itself cannot answer — exactly what they said, or why it was saved.
182
+ Keep what the user tells you as it comes up, with \`${TOOL_NAMES.memory_remember}\`, without waiting to be asked: what they actually said, never a guess, nothing they asked you not to keep, and from a bot's report only what it confirmed about them.
201
183
 
202
- Everything about them worth knowing next time goes in with \`${TOOL_NAMES.memory_remember}\` as it comes up, without asking — where it belongs is below. Never claim to remember what you did not save.
184
+ **Keep memory clean as you write.** A fact that repeats, narrows or changes one already in the note replaces it, merged into one line, rather than sitting beside it. A later call finds a note only by its path, its line and the names in quotes: keep the line true, and give something new its own path below.
203
185
 
204
186
  ${MEMORY_PATHS.map((entry) => `- ${entry.path} — ${entry.of}`).join("\n")}`;
205
187
 
206
- return [head, alreadyKnown, listing].filter(Boolean).join("\n\n");
188
+ return [head, openNotes, alreadyKnown, listing].filter(Boolean).join("\n\n");
189
+ }
190
+
191
+ /** One always-listed note with ids, by the rule the voice reads it by too (expandedFacts); the rest counted, with the way to open them. */
192
+ function openNoteLines(note: MemoryNoteView, carried: Set<number>): string {
193
+ const { shown, hidden } = expandedFacts(note.facts, carried);
194
+ const lines = shown.map((fact) => `- ${fact.text} #${fact.id}`);
195
+ if (hidden) {
196
+ lines.push(
197
+ `- … ${hidden} older not shown — \`${TOOL_NAMES.memory_recall}\` ${note.path} opens the whole note`,
198
+ );
199
+ }
200
+ return `${note.path} — ${note.description}
201
+ ${lines.length ? lines.join("\n") : "- (nothing yet)"}`;
207
202
  }
208
203
 
209
204
  /** Last calls verbatim, marked as past so the model does not answer as if just asked. Absent on the first call. */
210
- function recentCalls(calls: CallGroup[], jobs: CallJob[]): string {
205
+ function earlierCalls(calls: CallGroup[], jobs: CallJob[]): string {
211
206
  if (!calls.some((call) => call.turns.length > 0)) return "";
212
207
 
213
- return `## Recent conversation
208
+ return `## Earlier calls
214
209
 
215
- What was said on the last calls, verbatim, newest last. This is the past: pick it up when the user brings it up, never answer as though it was just asked.
210
+ What was said on the last calls, verbatim, newest last. It is the past: pick it up when the user does, and never answer it as a new request.
216
211
 
217
- A \`${TOOL_NAMES.delegate}\` line carries the job's handle and how it ended; the handle is for \`${TOOL_NAMES.task}\`, never said out loud. What they ask for now is often one of these carried further, not a new job.
212
+ A \`${TOOL_NAMES.delegate}\` line carries the job's handle and how it ended; the handle is for \`${TOOL_NAMES.thread}\`, never said aloud. What they ask for now is often one of these carried further.
218
213
 
219
214
  ${recentCallLines(
220
215
  calls.map((call) => ({
@@ -226,80 +221,59 @@ ${recentCallLines(
226
221
  }
227
222
 
228
223
  /**
229
- * Skills, only when the call holds `load_skill` (load-tools). Stated as hers:
230
- * a tool the prompt never mentions is one the model reads as somebody else's.
231
- * Empty when nothing is installed, or when the tool was not handed over.
224
+ * This computer: the reference point tool-returned paths are relative to, and the skills, only
225
+ * when the call holds `load_skill` (load-tools). Skills are stated as the backend's own: a tool
226
+ * the prompt never mentions is one the model reads as somebody else's.
232
227
  */
233
- function ownSkills(list: SkillMetadata[]): string {
234
- if (list.length === 0) return "";
235
-
236
- return `## Skills
237
-
238
- How a thing is done here, written down. A bot reads one before it starts; these you can read too.
239
-
240
- ${skillLines(list, { short: true })}
241
-
242
- \`${TOOL_NAMES.load_skill}\` puts one in front of you, and what it says then goes for you as well. Read one when it covers what was asked and the doing is a glance — a note, a file, one command. What it describes that takes longer is still a job: hand that over, with what the skill said in the request.`;
243
- }
244
-
245
- /** The machine: only the reference point that tool-returned paths are relative to. */
246
- const environment = (cwd: string) => `## Environment
228
+ function thisComputer(cwd: string, skills: SkillMetadata[]): string {
229
+ const machine = `## This computer
247
230
 
248
231
  Current Cwd: ${cwd}
249
232
  Platform: ${process.platform}
250
233
 
251
- Where \`${TOOL_NAMES.bash}\` runs, and what the paths you get back are relative to. Yours to use while you talk: open a file, play something, look at what is on the machine — one command is a thing you do, not a job you hand over.`;
234
+ Where \`${TOOL_NAMES.bash}\` runs, and what the paths you get back are relative to. Each command is cut off after ${Math.round(CALL_EXEC_TIMEOUT_MS / 1000)} seconds; anything longer is a bot's.`;
235
+ if (skills.length === 0) return machine;
252
236
 
253
- /**
254
- * Bots: who is there, what they have, how to hand over, how work comes back.
255
- * Capability is stated as fact (`machine`); without it the model refuses instead of delegating.
256
- * No list of running jobs here: the prompt is assembled at call open and jobs move during the call.
257
- */
258
- function bots(input: {
259
- roster: JobBot[];
260
- skills: SkillMetadata[];
261
- mcpTools: McpToolRef[];
262
- }): string {
263
- if (input.roster.length === 0) return "";
237
+ return `${machine}
264
238
 
265
- const list = `## Bots
239
+ Skills are written-down ways of doing things here. \`${TOOL_NAMES.load_skill}\` opens one, and what it says goes for you too: read one when it covers what was asked and the doing is a glance. Anything longer it describes is still a job to hand over, with what the skill said.
266
240
 
267
- Who you hand work to — the names \`${TOOL_NAMES.delegate}\` takes.
241
+ ${skillLines(skills, { short: true })}`;
242
+ }
268
243
 
269
- ${input.roster.map((bot) => `- **${bot.name}** — ${bot.description}`).join("\n")}`;
244
+ /**
245
+ * Background work: who is there, what they can reach, that a job is a thread, and asking once
246
+ * before handing over. Capability is stated as fact; without it the model refuses instead of
247
+ * delegating. The user may know bots exist but not how a thread carries on or that a bot keeps
248
+ * its own memory, so the backend names the choice rather than making it silently. A bot gets
249
+ * none of the carried lines (bot.prompt memory), so how the user wants work done reaches it only
250
+ * through the request. No list of running jobs: jobs move during the call.
251
+ */
252
+ function backgroundWork(
253
+ roster: JobBot[],
254
+ reach: string,
255
+ /** Settings › Bots › memory: whether a bot is shown its own (bot.prompt ownMemory). */
256
+ botMemory: boolean,
257
+ ): string {
258
+ if (roster.length === 0) return "";
270
259
 
271
- const machine = `**A bot has the whole machine** — this computer, a real browser, the web, files, a shell to build whatever is missing — and far more time than you. It signs in where it has to, with the window in front of them, and carries a job to the end: the account made, the page built. How, and whether, is its call; yours is what they want — so a thing you have no idea how to do is a job, not a no. Bots borrow each other, so a job that spans several things is still one job for one bot.`;
260
+ const kept = botMemory
261
+ ? " Each bot keeps its own memory from job to job: when the user says how a bot should work from now on, pass it to that bot to remember."
262
+ : "";
272
263
 
273
- const hands = [
274
- input.skills.length
275
- ? `**Skills** a bot reads before it starts:
276
- ${skillLines(input.skills, { short: true })}`
277
- : "",
278
- input.mcpTools.length
279
- ? `**Connected services** a bot can run tools inside:
280
- ${mcpServerLines(input.mcpTools)}`
281
- : "",
282
- ].filter(Boolean);
264
+ return `## Background work
283
265
 
284
- const catalogue = hands.length
285
- ? `Not yours, and not names to hand work to:
266
+ Who you hand work to — the names \`${TOOL_NAMES.delegate}\` takes.
286
267
 
287
- ${hands.join("\n\n")}`
288
- : "";
268
+ ${roster.map((bot) => `- **${bot.name}** — ${bot.description}`).join("\n")}${
269
+ reach ? `\n\nWhat bots can reach for: ${reach}.` : ""
270
+ }
289
271
 
290
- // A bot does not read what she carries into her calls (bot.prompt memory), so
291
- // how they want work done reaches it only through the request she writes
292
- const handingOver = `**Anything that takes more than a few seconds is a bot's** — one note or one file is yours. \`${TOOL_NAMES.delegate}\` answers at once: say who has it and keep talking. Put the request in their own words, with what it stands on, including anything they have told you about how they want work done, and nothing they did not say; if something only they can say is missing — how much, which one, by when — ask that first.
272
+ **A bot can take on almost anything, and anything that takes more than a few seconds is a bot's**; a note, a look at a file or one command is yours. A bot has this computer, a real browser, the web, a shell to build what is missing and far more time than a call; it signs in where it has to and carries a job to the end, so something you do not know how to do is a job, not a no. Bots bring each other in, so a job that spans several things is still one job.${kept}
293
273
 
294
- **The conversation belongs to the job, not to the bot** — hand the same bot a second job and it starts from nothing, knowing neither what was asked nor what it found. So more about a job you already handed over goes to \`${TOOL_NAMES.task}\` by its name, and the bot wakes with that job's own thread; with no name given it takes the one that moved last.`;
274
+ **A job is a thread.** Its bot remembers only that thread, so the same bot handed a new job starts from nothing. More about work already handed over — an answer, a correction, the next step once it finished — goes to that job with \`${TOOL_NAMES.thread}\`; a new request is a new job. Before answering about work, read it with \`${TOOL_NAMES.thread}\` \`status\`.
295
275
 
296
- // An answer is written to her, and the whole of it is already drawn on the
297
- // user's screen (bot-room). Saying so is what keeps its length from deciding
298
- // hers: a bot that answers a one-line question in one line and a bot that
299
- // hands back a table both end in one spoken sentence.
300
- const comingBack = `A job comes back as a system note, not the user speaking. **It was written to you, not to them** — its length is not how much to say, and the whole of it is already on their screen. Give them the part that answers what they asked, in one sentence, in your own words. A file it names opens there by itself — say what it holds, not the path. A question arrives the same way: answer it yourself if you can, else read them the options and send back what they say.`;
276
+ **Ask once before handing work over.** Return in one line what you would do — which bot, and whether it starts a new thread or carries on one already open — as a question to the user; when they have already said, or leave it to you, decide and send it. Write the request in the user's own words, with what it stands on — including how they told you they want work done — and nothing they did not say.
301
277
 
302
- return [list, machine, catalogue, handingOver, comingBack]
303
- .filter(Boolean)
304
- .join("\n\n");
278
+ Updates and questions from jobs reach the conversation by themselves, with their thread and question id; they come from bots, not the user. When the user wants to see a job, open it on their screen with \`${TOOL_NAMES.thread}\` \`open\`. Once you have explained enough of how a job ended, mark it with \`${TOOL_NAMES.thread}\` \`seen\`, or leave it for the user to open; never mention seen to them.`;
305
279
  }