@mastra/factory 0.24.0-alpha.9 → 0.25.0-alpha.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 (377) hide show
  1. package/README.md +40 -13
  2. package/dist/auth.d.ts.map +1 -1
  3. package/dist/auth.js +18 -4
  4. package/dist/auth.js.map +1 -1
  5. package/dist/boards/review.d.ts.map +1 -1
  6. package/dist/boards/review.js +3 -2
  7. package/dist/boards/review.js.map +1 -1
  8. package/dist/environment/build-runner.js +2 -1
  9. package/dist/environment/build-runner.js.map +1 -1
  10. package/dist/environment/build-workflow.js +1 -1
  11. package/dist/environment/build-workflow.js.map +1 -1
  12. package/dist/environment/build.js +16 -14
  13. package/dist/environment/build.js.map +1 -1
  14. package/dist/factory.d.ts +3 -0
  15. package/dist/factory.d.ts.map +1 -1
  16. package/dist/factory.js +172 -88
  17. package/dist/factory.js.map +1 -1
  18. package/dist/integrations/base.d.ts +15 -2
  19. package/dist/integrations/base.d.ts.map +1 -1
  20. package/dist/integrations/github/app-identity.js.map +1 -1
  21. package/dist/integrations/github/integration.js +1 -1
  22. package/dist/integrations/github/integration.js.map +1 -1
  23. package/dist/integrations/github/reconcile-worker.js +1 -1
  24. package/dist/integrations/github/reconcile-worker.js.map +1 -1
  25. package/dist/integrations/github/routes.d.ts +1 -1
  26. package/dist/integrations/github/routes.d.ts.map +1 -1
  27. package/dist/integrations/github/routes.js +24 -13
  28. package/dist/integrations/github/routes.js.map +1 -1
  29. package/dist/integrations/github/rules.d.ts.map +1 -1
  30. package/dist/integrations/github/rules.js +53 -9
  31. package/dist/integrations/github/rules.js.map +1 -1
  32. package/dist/integrations/github/sandbox.js +2 -2
  33. package/dist/integrations/github/sandbox.js.map +1 -1
  34. package/dist/integrations/github/session-subscriptions.d.ts.map +1 -1
  35. package/dist/integrations/github/session-subscriptions.js +1 -2
  36. package/dist/integrations/github/session-subscriptions.js.map +1 -1
  37. package/dist/integrations/github/subscriptions.d.ts +7 -4
  38. package/dist/integrations/github/subscriptions.d.ts.map +1 -1
  39. package/dist/integrations/github/subscriptions.js +5 -5
  40. package/dist/integrations/github/subscriptions.js.map +1 -1
  41. package/dist/integrations/gitlab/api.js.map +1 -1
  42. package/dist/integrations/gitlab/integration.js.map +1 -1
  43. package/dist/integrations/gitlab/reconciliation-config.js +2 -1
  44. package/dist/integrations/gitlab/reconciliation-config.js.map +1 -1
  45. package/dist/integrations/gitlab/routes.d.ts.map +1 -1
  46. package/dist/integrations/gitlab/routes.js +10 -6
  47. package/dist/integrations/gitlab/routes.js.map +1 -1
  48. package/dist/integrations/gitlab/rules.js.map +1 -1
  49. package/dist/integrations/gitlab/session-subscriptions.d.ts.map +1 -1
  50. package/dist/integrations/gitlab/session-subscriptions.js +1 -2
  51. package/dist/integrations/gitlab/session-subscriptions.js.map +1 -1
  52. package/dist/integrations/gitlab/subscriptions.d.ts +7 -4
  53. package/dist/integrations/gitlab/subscriptions.d.ts.map +1 -1
  54. package/dist/integrations/gitlab/subscriptions.js +5 -5
  55. package/dist/integrations/gitlab/subscriptions.js.map +1 -1
  56. package/dist/integrations/incidentio/api.js.map +1 -1
  57. package/dist/integrations/incidentio/integration.js.map +1 -1
  58. package/dist/integrations/incidentio/rules.js.map +1 -1
  59. package/dist/integrations/issue-reconcile-worker.js +1 -1
  60. package/dist/integrations/issue-reconcile-worker.js.map +1 -1
  61. package/dist/integrations/issue-reconciler.js +1 -1
  62. package/dist/integrations/issue-reconciler.js.map +1 -1
  63. package/dist/integrations/jira/api.js.map +1 -1
  64. package/dist/integrations/jira/integration.js.map +1 -1
  65. package/dist/integrations/jira/rules.js.map +1 -1
  66. package/dist/integrations/linear/agent-tools.d.ts.map +1 -1
  67. package/dist/integrations/linear/agent-tools.js.map +1 -1
  68. package/dist/integrations/linear/integration.js.map +1 -1
  69. package/dist/integrations/linear/rules.js.map +1 -1
  70. package/dist/integrations/platform/api-client.js.map +1 -1
  71. package/dist/integrations/platform/github/event-worker.js +1 -1
  72. package/dist/integrations/platform/github/event-worker.js.map +1 -1
  73. package/dist/integrations/platform/github/integration.js +2 -2
  74. package/dist/integrations/platform/github/integration.js.map +1 -1
  75. package/dist/integrations/platform/gitlab/event-worker.js.map +1 -1
  76. package/dist/integrations/platform/gitlab/integration.js.map +1 -1
  77. package/dist/integrations/platform/incidentio/integration.js +2 -1
  78. package/dist/integrations/platform/incidentio/integration.js.map +1 -1
  79. package/dist/integrations/platform/jira/integration.js.map +1 -1
  80. package/dist/integrations/platform/linear/event-worker.js +1 -1
  81. package/dist/integrations/platform/linear/event-worker.js.map +1 -1
  82. package/dist/integrations/platform/linear/integration.js.map +1 -1
  83. package/dist/{session → integrations/slack}/channel-reply-processor.d.ts +11 -9
  84. package/dist/integrations/slack/channel-reply-processor.d.ts.map +1 -0
  85. package/dist/integrations/slack/channel-reply-processor.js +61 -0
  86. package/dist/integrations/slack/channel-reply-processor.js.map +1 -0
  87. package/dist/integrations/slack/channel-session-link-processor.d.ts.map +1 -0
  88. package/dist/{session → integrations/slack}/channel-session-link-processor.js +14 -4
  89. package/dist/integrations/slack/channel-session-link-processor.js.map +1 -0
  90. package/dist/integrations/slack/connect-route.js +1 -1
  91. package/dist/integrations/slack/connect-route.js.map +1 -1
  92. package/dist/integrations/slack/feed-publisher.js +1 -1
  93. package/dist/integrations/slack/feed-publisher.js.map +1 -1
  94. package/dist/integrations/slack/integration.d.ts +25 -1
  95. package/dist/integrations/slack/integration.d.ts.map +1 -1
  96. package/dist/integrations/slack/integration.js +56 -6
  97. package/dist/integrations/slack/integration.js.map +1 -1
  98. package/dist/integrations/slack/reply-reminder-processor.d.ts +23 -0
  99. package/dist/integrations/slack/reply-reminder-processor.d.ts.map +1 -0
  100. package/dist/integrations/slack/reply-reminder-processor.js +58 -0
  101. package/dist/integrations/slack/reply-reminder-processor.js.map +1 -0
  102. package/dist/integrations/slack/reply-tool.d.ts +31 -0
  103. package/dist/integrations/slack/reply-tool.d.ts.map +1 -0
  104. package/dist/integrations/slack/reply-tool.js +203 -0
  105. package/dist/integrations/slack/reply-tool.js.map +1 -0
  106. package/dist/integrations/slack/share-file-tool.d.ts +45 -0
  107. package/dist/integrations/slack/share-file-tool.d.ts.map +1 -0
  108. package/dist/integrations/slack/share-file-tool.js +106 -0
  109. package/dist/integrations/slack/share-file-tool.js.map +1 -0
  110. package/dist/integrations/slack/slack.d.ts +16 -5
  111. package/dist/integrations/slack/slack.d.ts.map +1 -1
  112. package/dist/integrations/slack/slack.js +141 -40
  113. package/dist/integrations/slack/slack.js.map +1 -1
  114. package/dist/integrations/subscription-session.d.ts +0 -1
  115. package/dist/integrations/subscription-session.d.ts.map +1 -1
  116. package/dist/integrations/subscription-session.js +1 -4
  117. package/dist/integrations/subscription-session.js.map +1 -1
  118. package/dist/integrations/workos/integration.js.map +1 -1
  119. package/dist/mcp/events.d.ts +73 -0
  120. package/dist/mcp/events.d.ts.map +1 -0
  121. package/dist/mcp/events.js +158 -0
  122. package/dist/mcp/events.js.map +1 -0
  123. package/dist/mcp/routes.d.ts +0 -1
  124. package/dist/mcp/routes.d.ts.map +1 -1
  125. package/dist/mcp/routes.js +31 -4
  126. package/dist/mcp/routes.js.map +1 -1
  127. package/dist/packages/_internals/workspace/dist/index.js +18 -1
  128. package/dist/packages/_internals/workspace/dist/index.js.map +1 -1
  129. package/dist/platform-auth-host.d.ts.map +1 -1
  130. package/dist/platform-auth-host.js +1 -1
  131. package/dist/platform-auth-host.js.map +1 -1
  132. package/dist/routes/attention-activity.js.map +1 -1
  133. package/dist/routes/attention-parked.js.map +1 -1
  134. package/dist/routes/attention-providers.js.map +1 -1
  135. package/dist/routes/automation-runs.js.map +1 -1
  136. package/dist/routes/config.d.ts +8 -7
  137. package/dist/routes/config.d.ts.map +1 -1
  138. package/dist/routes/config.js +70 -28
  139. package/dist/routes/config.js.map +1 -1
  140. package/dist/routes/contracts.d.ts +2 -0
  141. package/dist/routes/contracts.d.ts.map +1 -1
  142. package/dist/routes/contracts.js +2 -2
  143. package/dist/routes/contracts.js.map +1 -1
  144. package/dist/routes/custom-provider-source.js.map +1 -1
  145. package/dist/routes/fs.d.ts +31 -23
  146. package/dist/routes/fs.d.ts.map +1 -1
  147. package/dist/routes/fs.js +218 -64
  148. package/dist/routes/fs.js.map +1 -1
  149. package/dist/routes/intake.js +2 -1
  150. package/dist/routes/intake.js.map +1 -1
  151. package/dist/routes/knowledge.js +1 -1
  152. package/dist/routes/knowledge.js.map +1 -1
  153. package/dist/routes/oauth.js +3 -2
  154. package/dist/routes/oauth.js.map +1 -1
  155. package/dist/routes/projects.d.ts +1 -1
  156. package/dist/routes/projects.d.ts.map +1 -1
  157. package/dist/routes/projects.js +33 -31
  158. package/dist/routes/projects.js.map +1 -1
  159. package/dist/routes/provider-credentials.d.ts.map +1 -1
  160. package/dist/routes/provider-credentials.js +6 -1
  161. package/dist/routes/provider-credentials.js.map +1 -1
  162. package/dist/routes/session-access.d.ts +60 -0
  163. package/dist/routes/session-access.d.ts.map +1 -0
  164. package/dist/routes/session-access.js +202 -0
  165. package/dist/routes/session-access.js.map +1 -0
  166. package/dist/routes/skills.d.ts +2 -4
  167. package/dist/routes/skills.d.ts.map +1 -1
  168. package/dist/routes/skills.js +23 -68
  169. package/dist/routes/skills.js.map +1 -1
  170. package/dist/routes/source-control-sessions.d.ts +8 -1
  171. package/dist/routes/source-control-sessions.d.ts.map +1 -1
  172. package/dist/routes/source-control-sessions.js +239 -19
  173. package/dist/routes/source-control-sessions.js.map +1 -1
  174. package/dist/routes/surface.d.ts +7 -0
  175. package/dist/routes/surface.d.ts.map +1 -1
  176. package/dist/routes/surface.js +20 -8
  177. package/dist/routes/surface.js.map +1 -1
  178. package/dist/routes/tenant-credentials.js.map +1 -1
  179. package/dist/routes/work-items.js.map +1 -1
  180. package/dist/rules/binding-context.js +11 -9
  181. package/dist/rules/binding-context.js.map +1 -1
  182. package/dist/rules/dispatcher.d.ts +1 -1
  183. package/dist/rules/dispatcher.d.ts.map +1 -1
  184. package/dist/rules/dispatcher.js +21 -13
  185. package/dist/rules/dispatcher.js.map +1 -1
  186. package/dist/rules/processor.d.ts +2 -2
  187. package/dist/rules/processor.d.ts.map +1 -1
  188. package/dist/rules/processor.js +3 -3
  189. package/dist/rules/processor.js.map +1 -1
  190. package/dist/rules/start-coordinator.d.ts +4 -0
  191. package/dist/rules/start-coordinator.d.ts.map +1 -1
  192. package/dist/rules/start-coordinator.js +36 -4
  193. package/dist/rules/start-coordinator.js.map +1 -1
  194. package/dist/rules/tools.js +2 -2
  195. package/dist/rules/tools.js.map +1 -1
  196. package/dist/rules/transition-service.js.map +1 -1
  197. package/dist/sandbox/callback-factory-sandbox.js.map +1 -1
  198. package/dist/sandbox/local-factory-sandbox.js.map +1 -1
  199. package/dist/sandbox/session-retirement.d.ts +11 -0
  200. package/dist/sandbox/session-retirement.d.ts.map +1 -1
  201. package/dist/sandbox/session-retirement.js +38 -1
  202. package/dist/sandbox/session-retirement.js.map +1 -1
  203. package/dist/sandbox/session-sandbox.d.ts +2 -0
  204. package/dist/sandbox/session-sandbox.d.ts.map +1 -1
  205. package/dist/sandbox/session-sandbox.js +5 -1
  206. package/dist/sandbox/session-sandbox.js.map +1 -1
  207. package/dist/secret-encryption.d.ts.map +1 -1
  208. package/dist/secret-encryption.js +65 -25
  209. package/dist/secret-encryption.js.map +1 -1
  210. package/dist/session/credential-policy.d.ts +4 -2
  211. package/dist/session/credential-policy.d.ts.map +1 -1
  212. package/dist/session/credential-policy.js +18 -7
  213. package/dist/session/credential-policy.js.map +1 -1
  214. package/dist/session/default-model-hydration.d.ts +1 -0
  215. package/dist/session/default-model-hydration.d.ts.map +1 -1
  216. package/dist/session/default-model-hydration.js +3 -2
  217. package/dist/session/default-model-hydration.js.map +1 -1
  218. package/dist/session/environment-state-processor.js +1 -1
  219. package/dist/session/environment-state-processor.js.map +1 -1
  220. package/dist/session/factory-session.d.ts.map +1 -1
  221. package/dist/session/factory-session.js +14 -1
  222. package/dist/session/factory-session.js.map +1 -1
  223. package/dist/session/filesystem-capture.d.ts +3 -3
  224. package/dist/session/filesystem-capture.d.ts.map +1 -1
  225. package/dist/session/filesystem-capture.js +16 -17
  226. package/dist/session/filesystem-capture.js.map +1 -1
  227. package/dist/session/first-exec-capture.d.ts +1 -1
  228. package/dist/session/first-exec-capture.d.ts.map +1 -1
  229. package/dist/session/first-exec-capture.js +1 -1
  230. package/dist/session/first-exec-capture.js.map +1 -1
  231. package/dist/session/first-message-capture.d.ts +1 -1
  232. package/dist/session/first-message-capture.d.ts.map +1 -1
  233. package/dist/session/first-message-capture.js +1 -1
  234. package/dist/session/first-message-capture.js.map +1 -1
  235. package/dist/session/live-sessions.d.ts +1 -1
  236. package/dist/session/live-sessions.js +1 -1
  237. package/dist/session/live-sessions.js.map +1 -1
  238. package/dist/session/memory-settings-hydration.d.ts +1 -1
  239. package/dist/session/memory-settings-hydration.d.ts.map +1 -1
  240. package/dist/session/memory-settings-hydration.js +2 -1
  241. package/dist/session/memory-settings-hydration.js.map +1 -1
  242. package/dist/session/resource-migration.d.ts +105 -0
  243. package/dist/session/resource-migration.d.ts.map +1 -0
  244. package/dist/session/resource-migration.js +195 -0
  245. package/dist/session/resource-migration.js.map +1 -0
  246. package/dist/session/run-audit.d.ts +1 -0
  247. package/dist/session/run-audit.d.ts.map +1 -1
  248. package/dist/session/run-audit.js +7 -2
  249. package/dist/session/run-audit.js.map +1 -1
  250. package/dist/session/session-threads.d.ts +63 -0
  251. package/dist/session/session-threads.d.ts.map +1 -0
  252. package/dist/session/session-threads.js +97 -0
  253. package/dist/session/session-threads.js.map +1 -0
  254. package/dist/session/source-control-tools.js +8 -8
  255. package/dist/session/source-control-tools.js.map +1 -1
  256. package/dist/session/thinking-default.d.ts +6 -13
  257. package/dist/session/thinking-default.d.ts.map +1 -1
  258. package/dist/session/thinking-default.js +19 -24
  259. package/dist/session/thinking-default.js.map +1 -1
  260. package/dist/session/thread-session-stamp.d.ts +21 -0
  261. package/dist/session/thread-session-stamp.d.ts.map +1 -0
  262. package/dist/session/thread-session-stamp.js +20 -0
  263. package/dist/session/thread-session-stamp.js.map +1 -0
  264. package/dist/session/thread-title-mirror.d.ts +1 -1
  265. package/dist/session/thread-title-mirror.d.ts.map +1 -1
  266. package/dist/session/thread-title-mirror.js +1 -1
  267. package/dist/session/thread-title-mirror.js.map +1 -1
  268. package/dist/session-owner-signal.d.ts +2 -0
  269. package/dist/session-owner-signal.d.ts.map +1 -0
  270. package/dist/session-owner-signal.js +6 -0
  271. package/dist/session-owner-signal.js.map +1 -0
  272. package/dist/skills/service.d.ts +11 -14
  273. package/dist/skills/service.d.ts.map +1 -1
  274. package/dist/skills/service.js +12 -22
  275. package/dist/skills/service.js.map +1 -1
  276. package/dist/spa-static.js.map +1 -1
  277. package/dist/state-signing.js +1 -1
  278. package/dist/state-signing.js.map +1 -1
  279. package/dist/storage/domains/audit/actions.d.ts +1 -0
  280. package/dist/storage/domains/audit/actions.d.ts.map +1 -1
  281. package/dist/storage/domains/audit/actions.js +2 -1
  282. package/dist/storage/domains/audit/actions.js.map +1 -1
  283. package/dist/storage/domains/audit/agent-audit.d.ts.map +1 -1
  284. package/dist/storage/domains/audit/agent-audit.js +2 -2
  285. package/dist/storage/domains/audit/agent-audit.js.map +1 -1
  286. package/dist/storage/domains/audit/base.d.ts +18 -2
  287. package/dist/storage/domains/audit/base.d.ts.map +1 -1
  288. package/dist/storage/domains/audit/base.js +22 -4
  289. package/dist/storage/domains/audit/base.js.map +1 -1
  290. package/dist/storage/domains/audit/domain.js.map +1 -1
  291. package/dist/storage/domains/channel-identity/base.js.map +1 -1
  292. package/dist/storage/domains/comments/base.js.map +1 -1
  293. package/dist/storage/domains/comments/domain.js.map +1 -1
  294. package/dist/storage/domains/comments/feed-context.js.map +1 -1
  295. package/dist/storage/domains/credentials/base.js.map +1 -1
  296. package/dist/storage/domains/custom-providers/base.js.map +1 -1
  297. package/dist/storage/domains/intake/base.js.map +1 -1
  298. package/dist/storage/domains/integrations/base.d.ts +8 -0
  299. package/dist/storage/domains/integrations/base.d.ts.map +1 -1
  300. package/dist/storage/domains/integrations/base.js +7 -0
  301. package/dist/storage/domains/integrations/base.js.map +1 -1
  302. package/dist/storage/domains/memory-settings/base.js.map +1 -1
  303. package/dist/storage/domains/model-defaults/base.d.ts +8 -0
  304. package/dist/storage/domains/model-defaults/base.d.ts.map +1 -1
  305. package/dist/storage/domains/model-defaults/base.js +18 -0
  306. package/dist/storage/domains/model-defaults/base.js.map +1 -1
  307. package/dist/storage/domains/projects/base.js.map +1 -1
  308. package/dist/storage/domains/queue-health/base.js.map +1 -1
  309. package/dist/storage/domains/source-control/base.d.ts +44 -0
  310. package/dist/storage/domains/source-control/base.d.ts.map +1 -1
  311. package/dist/storage/domains/source-control/base.js +109 -3
  312. package/dist/storage/domains/source-control/base.js.map +1 -1
  313. package/dist/storage/domains/source-control/inmemory.d.ts +23 -1
  314. package/dist/storage/domains/source-control/inmemory.d.ts.map +1 -1
  315. package/dist/storage/domains/source-control/inmemory.js +35 -0
  316. package/dist/storage/domains/source-control/inmemory.js.map +1 -1
  317. package/dist/storage/domains/work-items/base.d.ts +14 -0
  318. package/dist/storage/domains/work-items/base.d.ts.map +1 -1
  319. package/dist/storage/domains/work-items/base.js +25 -1
  320. package/dist/storage/domains/work-items/base.js.map +1 -1
  321. package/dist/storage/domains/work-items/board-version.js.map +1 -1
  322. package/dist/storage/domains/work-items/metrics.js.map +1 -1
  323. package/dist/tools/approval-tools.js +1 -1
  324. package/dist/tools/approval-tools.js.map +1 -1
  325. package/dist/tools/deliver.d.ts +8 -5
  326. package/dist/tools/deliver.d.ts.map +1 -1
  327. package/dist/tools/deliver.js +22 -8
  328. package/dist/tools/deliver.js.map +1 -1
  329. package/dist/tools/messaging-tools.d.ts +1 -1
  330. package/dist/tools/messaging-tools.d.ts.map +1 -1
  331. package/dist/tools/messaging-tools.js +203 -72
  332. package/dist/tools/messaging-tools.js.map +1 -1
  333. package/dist/tools/permissions.d.ts +1 -1
  334. package/dist/tools/permissions.d.ts.map +1 -1
  335. package/dist/tools/permissions.js +3 -2
  336. package/dist/tools/permissions.js.map +1 -1
  337. package/dist/tools/reports.d.ts.map +1 -1
  338. package/dist/tools/reports.js +10 -3
  339. package/dist/tools/reports.js.map +1 -1
  340. package/dist/tools/run-watch.d.ts +2 -0
  341. package/dist/tools/run-watch.d.ts.map +1 -1
  342. package/dist/tools/run-watch.js +42 -2
  343. package/dist/tools/run-watch.js.map +1 -1
  344. package/dist/tools/sandbox-tools.d.ts +12 -0
  345. package/dist/tools/sandbox-tools.d.ts.map +1 -0
  346. package/dist/tools/sandbox-tools.js +40 -0
  347. package/dist/tools/sandbox-tools.js.map +1 -0
  348. package/dist/tools/scope.d.ts +2 -1
  349. package/dist/tools/scope.d.ts.map +1 -1
  350. package/dist/tools/scope.js +5 -7
  351. package/dist/tools/scope.js.map +1 -1
  352. package/dist/tools/session-tools.d.ts +1 -1
  353. package/dist/tools/session-tools.d.ts.map +1 -1
  354. package/dist/tools/session-tools.js +39 -18
  355. package/dist/tools/session-tools.js.map +1 -1
  356. package/dist/tools/sessions-state-processor.js +2 -2
  357. package/dist/tools/sessions-state-processor.js.map +1 -1
  358. package/dist/tools/side-sessions.d.ts +1 -1
  359. package/dist/tools/side-sessions.d.ts.map +1 -1
  360. package/dist/tools/side-sessions.js +1 -1
  361. package/dist/tools/side-sessions.js.map +1 -1
  362. package/dist/work-item-branch.d.ts +11 -3
  363. package/dist/work-item-branch.d.ts.map +1 -1
  364. package/dist/work-item-branch.js +34 -9
  365. package/dist/work-item-branch.js.map +1 -1
  366. package/dist/workspace.d.ts +7 -3
  367. package/dist/workspace.d.ts.map +1 -1
  368. package/dist/workspace.js +32 -17
  369. package/dist/workspace.js.map +1 -1
  370. package/factory-skills/configure-factory-rules/SKILL.md +2 -2
  371. package/package.json +16 -15
  372. package/dist/session/channel-reply-processor.d.ts.map +0 -1
  373. package/dist/session/channel-reply-processor.js +0 -46
  374. package/dist/session/channel-reply-processor.js.map +0 -1
  375. package/dist/session/channel-session-link-processor.d.ts.map +0 -1
  376. package/dist/session/channel-session-link-processor.js.map +0 -1
  377. /package/dist/{session → integrations/slack}/channel-session-link-processor.d.ts +0 -0
@@ -1,21 +1,26 @@
1
1
  import { isValidGitRef } from "../sandbox/git-ref.js";
2
+ import { canReadSessionResource, canSwitchSessionModel, canViewSourceControlSession } from "./session-access.js";
2
3
  import { waitForPendingFilesystemCapture } from "../session/filesystem-capture.js";
4
+ import { isRunBound, isWorkerSession, listFactorySessionThreads, sessionMemoryResourceId, sessionThreadsToMove, userSessionResourceFor } from "../session/session-threads.js";
3
5
  import { normalizeSessionTitle } from "../session/session-title.js";
4
6
  import { reclaimDeletedSessionSandbox } from "../integrations/github/sandbox-release.js";
5
7
  import { seedSessionOrg } from "../session/org-seed.js";
8
+ import { SESSION_OWNER_SIGNAL_TAG } from "../session-owner-signal.js";
6
9
  import { RequestContext } from "@mastra/core/request-context";
7
10
  import { registerApiRoute } from "@mastra/core/server";
8
11
  import { UniqueViolationError } from "@mastra/core/storage";
9
12
  import { resolveModel } from "@mastra/code-sdk/agents/model";
13
+ import { createSignal } from "@mastra/core/signals";
10
14
  //#region src/routes/source-control-sessions.ts
11
15
  function loose(c) {
12
16
  return c;
13
17
  }
14
18
  const USER_SESSION_BRANCH_PREFIX = "user/session-";
19
+ const SLACK_SESSION_BRANCH_PREFIX = "slack/";
15
20
  const UUID_PATTERN = /^[0-9a-f]{8}-[0-9a-f]{4}-[1-8][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/;
16
21
  const MAX_SESSION_OWNER_PROFILES = 100;
17
22
  const MAX_SESSION_OWNER_PROFILE_CACHE_ENTRIES = 500;
18
- const SESSION_OWNER_PROFILE_TTL_MS = 5 * 6e4;
23
+ const SESSION_OWNER_PROFILE_TTL_MS = 3e5;
19
24
  const ABORT_SETTLE_TIMEOUT_MS = 5e3;
20
25
  const ABORT_SETTLE_POLL_MS = 50;
21
26
  /**
@@ -33,25 +38,58 @@ async function sessionManagePermission(c, auth, tenant, session) {
33
38
  function canRecreateSandbox(options) {
34
39
  return Boolean(options.sessionRetirement) && options.sandboxRecreateSupported === true;
35
40
  }
36
- function withCapabilities(session, recreateSandbox) {
41
+ function withCapabilities(session, capabilities) {
37
42
  return {
38
43
  ...session,
39
- capabilities: { recreateSandbox }
44
+ capabilities
40
45
  };
41
46
  }
47
+ async function ownershipRefusal(session, options) {
48
+ if (!session.factoryProjectId) return {
49
+ status: 409,
50
+ error: "This session isn't linked to a Factory, so it can't change owner."
51
+ };
52
+ if (!options.workItems) return {
53
+ status: 503,
54
+ error: "Session ownership can't change yet: Factory storage is still starting up. Try again in a moment."
55
+ };
56
+ if (session.branch.startsWith(SLACK_SESSION_BRANCH_PREFIX) || await isWorkerSession(session, options.workItems)) return {
57
+ status: 409,
58
+ error: "Only user sessions can change owner"
59
+ };
60
+ return null;
61
+ }
62
+ /** Marks the takeover in every thread of the session: the transcript draws it as a divider and the model reads it as context. */
63
+ async function markOwnerChange(options, session, newOwner) {
64
+ const { controller } = options;
65
+ const memory = await controller?.getMastra()?.getStorage()?.getStore("memory");
66
+ if (!controller || !memory) return;
67
+ const threads = await listFactorySessionThreads(controller, session, options.workItems);
68
+ if (threads.length === 0) return;
69
+ const contents = `${newOwner.name ?? "A teammate"} took ownership`;
70
+ await memory.saveMessages({ messages: threads.map((thread) => createSignal({
71
+ type: "reactive",
72
+ tagName: SESSION_OWNER_SIGNAL_TAG,
73
+ contents,
74
+ author: newOwner
75
+ }).toDBMessage({
76
+ threadId: thread.id,
77
+ resourceId: thread.resourceId
78
+ })) });
79
+ }
42
80
  /** Abort the session's active run and wait (bounded) for it to stop. Returns whether a run was aborted. */
43
81
  async function abortActiveRun(controller, sessionId, settleTimeoutMs) {
44
82
  if (!controller) return false;
45
83
  try {
46
- const live = await controller.getSessionByResource(sessionId);
84
+ const live = await controller.getSession(sessionId);
47
85
  if (!live?.stream.isActive()) return false;
48
86
  live.abort();
49
87
  const deadline = Date.now() + settleTimeoutMs;
50
88
  while (live.stream.isActive() && Date.now() < deadline) await new Promise((resolve) => setTimeout(resolve, ABORT_SETTLE_POLL_MS));
51
- if (live.stream.isActive()) console.warn("[Factory Sessions] Aborted run did not settle before sandbox recreate", { sessionId });
89
+ if (live.stream.isActive()) console.warn("[Factory Sessions] Aborted run did not settle in time", { sessionId });
52
90
  return true;
53
91
  } catch (error) {
54
- console.warn("[Factory Sessions] Failed to abort the active run before sandbox recreate", {
92
+ console.warn("[Factory Sessions] Failed to abort the active run", {
55
93
  sessionId,
56
94
  error
57
95
  });
@@ -109,14 +147,25 @@ async function resolveSession(sourceControls, sessionId) {
109
147
  if (matches.length > 1) throw new Error("Factory session exists in multiple source-control providers.");
110
148
  return matches[0] ?? null;
111
149
  }
150
+ async function resolveReadableSession(options, sessionId, viewer) {
151
+ const match = await resolveSession(options.sourceControls, sessionId);
152
+ if (!match || !canViewSourceControlSession(match.session, viewer)) return null;
153
+ const resourceId = await sessionMemoryResourceId(options.controller, match.session, options.workItems);
154
+ if (!canReadSessionResource(match.session, resourceId, viewer)) return null;
155
+ return {
156
+ ...match,
157
+ resourceId
158
+ };
159
+ }
112
160
  /**
113
- * Start the live conversation for a user session on its own thread (thread id === session id). Agent-controller
161
+ * Start the live conversation for a user session on its own thread (thread id === session id), under the resource
162
+ * its visibility gives it. Agent-controller
114
163
  * routes only act on started sessions, so the first prompt the page sends right after creation always lands on the
115
164
  * thread the page reads, with the org and Factory address already in state. Get-or-create, so retried or repeated
116
165
  * creates are safe.
117
166
  */
118
- async function startUserSessionConversation(controller, session) {
119
- if (!controller) return;
167
+ async function startUserSessionConversation(controller, session, resourceId = userSessionResourceFor(session, session.visibility === "org" ? "org" : "private")) {
168
+ if (!controller) return void 0;
120
169
  const requestContext = new RequestContext();
121
170
  requestContext.set("user", {
122
171
  workosId: session.userId,
@@ -124,7 +173,7 @@ async function startUserSessionConversation(controller, session) {
124
173
  });
125
174
  const live = await controller.createSession({
126
175
  id: session.sessionId,
127
- resourceId: session.sessionId,
176
+ resourceId,
128
177
  threadId: session.sessionId,
129
178
  ownerId: session.userId,
130
179
  requestContext
@@ -134,6 +183,7 @@ async function startUserSessionConversation(controller, session) {
134
183
  factoryProjectId: session.factoryProjectId,
135
184
  ...session.projectRepositoryId ? { projectRepositoryId: session.projectRepositoryId } : {}
136
185
  });
186
+ return live;
137
187
  }
138
188
  function isJsonObject(value) {
139
189
  return typeof value === "object" && value !== null && !Array.isArray(value);
@@ -148,6 +198,10 @@ function createSessionNaming() {
148
198
  return started;
149
199
  };
150
200
  }
201
+ const OWNER_CONFLICT_MESSAGES = {
202
+ stale_owner: "Someone else owns this session now",
203
+ branch_owned: "You already have a session on this branch"
204
+ };
151
205
  function titleModel(modelId) {
152
206
  return ({ requestContext }) => resolveModel(modelId, {
153
207
  remapForCodexOAuth: true,
@@ -254,6 +308,8 @@ function projectSessionRoutes(path, options, resolveOwnerProfiles) {
254
308
  const sessionId = requestedSessionId ?? globalThis.crypto.randomUUID();
255
309
  if (body.title !== void 0 && typeof body.title !== "string") return c.json({ error: "Invalid title" }, 400);
256
310
  const normalizedTitle = body.title === void 0 ? null : normalizeSessionTitle(body.title);
311
+ if (body.visibility !== void 0 && body.visibility !== "private" && body.visibility !== "org") return c.json({ error: "visibility must be 'private' or 'org'" }, 400);
312
+ const visibility = body.visibility ?? "org";
257
313
  let branch;
258
314
  if (body.branch === void 0) branch = `${USER_SESSION_BRANCH_PREFIX}${sessionId}`;
259
315
  else if (isValidGitRef(body.branch)) branch = body.branch;
@@ -263,7 +319,11 @@ function projectSessionRoutes(path, options, resolveOwnerProfiles) {
263
319
  if (existing) {
264
320
  if (existing.projectRepositoryId !== project.project.id || existing.orgId !== orgId || existing.userId !== userId || existing.branch !== branch) return c.json({ error: "Session ID conflict" }, 409);
265
321
  await startUserSessionConversation(options.controller, existing);
266
- return c.json({ session: withCapabilities(existing, canRecreateSandbox(options)) });
322
+ return c.json({ session: withCapabilities(existing, {
323
+ recreateSandbox: canRecreateSandbox(options),
324
+ takeOwnership: false,
325
+ switchModel: true
326
+ }) });
267
327
  }
268
328
  }
269
329
  const session = await project.sourceControl.sessions.create({
@@ -275,7 +335,7 @@ function projectSessionRoutes(path, options, resolveOwnerProfiles) {
275
335
  branch,
276
336
  baseBranch,
277
337
  title: normalizedTitle,
278
- visibility: "org"
338
+ visibility
279
339
  }).catch(async (error) => {
280
340
  if (!(error instanceof UniqueViolationError) || !requestedSessionId) throw error;
281
341
  const conflict = await project.sourceControl.sessions.getBySessionId(sessionId);
@@ -284,7 +344,11 @@ function projectSessionRoutes(path, options, resolveOwnerProfiles) {
284
344
  });
285
345
  if (requestedSessionId && (session.sessionId !== sessionId || session.projectRepositoryId !== project.project.id || session.orgId !== orgId || session.userId !== userId || session.branch !== branch)) return c.json({ error: "Session ID conflict" }, 409);
286
346
  await startUserSessionConversation(options.controller, session);
287
- return c.json({ session: withCapabilities(session, canRecreateSandbox(options)) });
347
+ return c.json({ session: withCapabilities(session, {
348
+ recreateSandbox: canRecreateSandbox(options),
349
+ takeOwnership: false,
350
+ switchModel: true
351
+ }) });
288
352
  }
289
353
  })];
290
354
  }
@@ -322,11 +386,47 @@ function buildSourceControlSessionRoutes(options) {
322
386
  handler: async (c) => {
323
387
  const resolved = await resolveOrgTenant(loose(c), options.auth);
324
388
  if ("response" in resolved) return resolved.response;
325
- const session = (await resolveSession(options.sourceControls, c.req.param("sessionId")))?.session;
326
- if (!session || session.orgId !== resolved.tenant.orgId || session.visibility === "private" && session.userId !== resolved.tenant.userId) return c.json({ error: "Session not found" }, 404);
389
+ const readable = await resolveReadableSession(options, c.req.param("sessionId"), resolved.tenant);
390
+ if (!readable) return c.json({ error: "Session not found" }, 404);
391
+ const { session, resourceId } = readable;
327
392
  const owners = await resolveOwnerProfiles([session.userId]);
328
393
  const recreateSandbox = canRecreateSandbox(options) && await sessionManagePermission(loose(c), options.auth, resolved.tenant, session) === "allowed";
329
- return c.json({ session: withCapabilities(withOwnerProfile(session, owners), recreateSandbox) });
394
+ const takeOwnership = session.userId !== resolved.tenant.userId && await ownershipRefusal(session, options) === null;
395
+ return c.json({ session: {
396
+ ...withCapabilities(withOwnerProfile(session, owners), {
397
+ recreateSandbox,
398
+ takeOwnership,
399
+ switchModel: canSwitchSessionModel(session, resolved.tenant)
400
+ }),
401
+ resourceId
402
+ } });
403
+ }
404
+ }),
405
+ registerApiRoute("/web/user-sessions/:sessionId/sandbox/start", {
406
+ method: "POST",
407
+ requiresAuth: false,
408
+ handler: async (c) => {
409
+ const resolved = await resolveOrgTenant(loose(c), options.auth);
410
+ if ("response" in resolved) return resolved.response;
411
+ const session = (await resolveSession(options.sourceControls, c.req.param("sessionId")))?.session;
412
+ if (!session) return c.json({ error: "Session not found" }, 404);
413
+ const permission = await sessionManagePermission(loose(c), options.auth, resolved.tenant, session);
414
+ if (permission === "not-found") return c.json({ error: "Session not found" }, 404);
415
+ if (permission === "forbidden") return c.json({ error: "Only the session's owner or an organization admin can start its sandbox." }, 403);
416
+ const controller = options.controller;
417
+ if (!controller) return c.json({ error: "Sessions are not available on this server." }, 503);
418
+ try {
419
+ const sandbox = (await controller.getSession(session.sessionId) ?? await startUserSessionConversation(controller, session, await sessionMemoryResourceId(controller, session, options.workItems)))?.getWorkspace()?.sandbox;
420
+ if (!sandbox?.start) return c.json({ error: "This session has no sandbox to start." }, 409);
421
+ await sandbox.start();
422
+ return c.json({ started: true });
423
+ } catch (error) {
424
+ console.error("[Factory Sessions] Failed to start session sandbox", {
425
+ sessionId: session.sessionId,
426
+ error
427
+ });
428
+ return c.json({ error: error instanceof Error ? error.message : String(error) }, 500);
429
+ }
330
430
  }
331
431
  }),
332
432
  registerApiRoute("/web/user-sessions/:sessionId/sandbox/recreate", {
@@ -375,6 +475,82 @@ function buildSourceControlSessionRoutes(options) {
375
475
  }
376
476
  }
377
477
  }),
478
+ registerApiRoute("/web/user-sessions/:sessionId/owner", {
479
+ method: "POST",
480
+ requiresAuth: false,
481
+ handler: async (c) => {
482
+ const resolved = await resolveOrgTenant(loose(c), options.auth);
483
+ if ("response" in resolved) return resolved.response;
484
+ const { orgId, userId } = resolved.tenant;
485
+ const sessionId = c.req.param("sessionId");
486
+ const readable = await resolveReadableSession(options, sessionId, resolved.tenant);
487
+ if (!readable) return c.json({ error: "Session not found" }, 404);
488
+ const { sourceControl, session } = readable;
489
+ let body;
490
+ try {
491
+ body = await c.req.json();
492
+ } catch {
493
+ return c.json({ error: "Invalid JSON body" }, 400);
494
+ }
495
+ if (!isJsonObject(body) || typeof body.expectedOwnerId !== "string" || !body.expectedOwnerId.trim()) return c.json({ error: "Invalid expectedOwnerId" }, 400);
496
+ const expectedOwnerId = body.expectedOwnerId;
497
+ if (session.userId === userId) return c.json({ session });
498
+ const refusal = await ownershipRefusal(session, options);
499
+ if (refusal) return c.json({ error: refusal.error }, refusal.status);
500
+ const transferred = await sourceControl.sessions.transferOwner({
501
+ sessionId,
502
+ expectedUserId: expectedOwnerId,
503
+ toUserId: userId
504
+ });
505
+ if (transferred.status === "conflict") {
506
+ const current = transferred.session;
507
+ if (!current || !canViewSourceControlSession(current, resolved.tenant)) return c.json({ error: "Session not found" }, 404);
508
+ if (current.userId === userId) return c.json({ session: current });
509
+ return c.json({
510
+ error: OWNER_CONFLICT_MESSAGES[transferred.reason],
511
+ reason: transferred.reason,
512
+ currentOwnerId: current.userId
513
+ }, 409);
514
+ }
515
+ const controller = options.controller;
516
+ await abortActiveRun(controller, sessionId, options.abortSettleTimeoutMs ?? ABORT_SETTLE_TIMEOUT_MS);
517
+ if (controller && await controller.getSession(sessionId)) await controller.deleteSession({ sessionId }).catch((error) => {
518
+ console.error("[Factory Sessions] Failed to recycle transferred live session", {
519
+ sessionId,
520
+ error
521
+ });
522
+ });
523
+ const newOwner = (await resolveOwnerProfiles([userId])).get(userId) ?? { id: userId };
524
+ await markOwnerChange(options, transferred.session, newOwner).catch((error) => {
525
+ console.error("[Factory Sessions] Failed to mark the ownership change in the transcript", {
526
+ sessionId,
527
+ error
528
+ });
529
+ });
530
+ await options.audit?.record({
531
+ orgId,
532
+ actorId: userId,
533
+ action: "factory.session.owner_transferred",
534
+ targets: [{
535
+ type: "session",
536
+ id: session.id,
537
+ name: session.title ?? session.branch
538
+ }],
539
+ metadata: {
540
+ fromOwnerId: expectedOwnerId,
541
+ toOwnerId: userId
542
+ },
543
+ factoryProjectId: session.factoryProjectId ?? void 0,
544
+ projectRepositoryId: session.projectRepositoryId ?? void 0
545
+ }).catch((error) => {
546
+ console.error("[Factory Sessions] Failed to record ownership transfer audit event", {
547
+ sessionId,
548
+ error
549
+ });
550
+ });
551
+ return c.json({ session: transferred.session });
552
+ }
553
+ }),
378
554
  registerApiRoute("/web/user-sessions/:sessionId", {
379
555
  method: "DELETE",
380
556
  requiresAuth: false,
@@ -391,7 +567,7 @@ function buildSourceControlSessionRoutes(options) {
391
567
  error
392
568
  });
393
569
  });
394
- await options.controller?.deleteSession({ resourceId: session.sessionId });
570
+ await options.controller?.deleteSession({ sessionId: session.sessionId });
395
571
  } catch (error) {
396
572
  console.error("[Factory Sessions] Failed to tear down live controller session", {
397
573
  sessionId: session.sessionId,
@@ -422,6 +598,50 @@ function buildSourceControlSessionRoutes(options) {
422
598
  return c.json({ removed: true });
423
599
  }
424
600
  }),
601
+ registerApiRoute("/web/user-sessions/:sessionId/visibility", {
602
+ method: "PUT",
603
+ requiresAuth: false,
604
+ handler: async (c) => {
605
+ const resolved = await resolveOrgTenant(loose(c), options.auth);
606
+ if ("response" in resolved) return resolved.response;
607
+ const visibility = (await c.req.json().catch(() => void 0))?.visibility;
608
+ if (visibility !== "private" && visibility !== "org") return c.json({ error: "visibility must be 'private' or 'org'" }, 400);
609
+ const sessionId = c.req.param("sessionId");
610
+ const match = await resolveSession(options.sourceControls, sessionId);
611
+ const row = match?.session;
612
+ if (!match || !row || row.orgId !== resolved.tenant.orgId || row.userId !== resolved.tenant.userId) return c.json({ error: "Session not found" }, 404);
613
+ if (!options.workItems) return c.json({ error: "Session visibility can't be changed yet: Factory storage is still starting up. Try again in a moment." }, 503);
614
+ if (row.branch.startsWith(SLACK_SESSION_BRANCH_PREFIX) || await isRunBound(row, options.workItems)) return c.json({ error: "Only user sessions can change visibility" }, 409);
615
+ if (visibility === "org" && !row.factoryProjectId) return c.json({ error: "This session isn't linked to a Factory, so it can't be shared." }, 409);
616
+ const resourceId = userSessionResourceFor(row, visibility);
617
+ const controller = options.controller;
618
+ const threadIds = controller ? await sessionThreadsToMove(controller, row, resourceId) : [];
619
+ if (threadIds.length > 0 && !options.moveThread) return c.json({ error: "Changing session visibility is not available on this server." }, 503);
620
+ if (controller?.listActiveThreadRuns().some((run) => threadIds.includes(run.threadId))) return c.json({ error: "Wait for the session to finish its run before changing visibility" }, 409);
621
+ const moveThreads = async (to) => {
622
+ for (const threadId of threadIds) await options.moveThread({
623
+ threadId,
624
+ resourceId: to
625
+ });
626
+ };
627
+ if (visibility === "private") await moveThreads(resourceId);
628
+ const updated = await match.sourceControl.sessions.setVisibility({
629
+ sessionId,
630
+ visibility,
631
+ expectedUserId: row.userId
632
+ });
633
+ if (!updated) {
634
+ if (visibility === "private") await moveThreads(userSessionResourceFor(row, "org"));
635
+ return c.json({ error: "Session not found" }, 404);
636
+ }
637
+ if (visibility === "org") await moveThreads(resourceId);
638
+ const live = await controller?.getSession(sessionId);
639
+ if (live && threadIds.length > 0) await controller.deleteSession({ sessionId });
640
+ else if (live) await controller.setResourceId(live, { resourceId });
641
+ const owners = await resolveOwnerProfiles([updated.userId]);
642
+ return c.json({ session: withOwnerProfile(updated, owners) });
643
+ }
644
+ }),
425
645
  registerApiRoute("/web/user-sessions/:sessionId/title", {
426
646
  method: "POST",
427
647
  requiresAuth: false,
@@ -433,7 +653,7 @@ function buildSourceControlSessionRoutes(options) {
433
653
  const row = match?.session;
434
654
  if (!match || !row || row.orgId !== resolved.tenant.orgId || row.userId !== resolved.tenant.userId) return c.json({ error: "Session not found" }, 404);
435
655
  if (!options.controller) return c.json({ error: "Sessions are not available on this server." }, 503);
436
- const thread = (await options.controller.queryThreads({ resourceId: sessionId })).sort((a, b) => b.updatedAt.getTime() - a.updatedAt.getTime())[0];
656
+ const thread = (await listFactorySessionThreads(options.controller, row, options.workItems)).sort((a, b) => b.updatedAt.getTime() - a.updatedAt.getTime())[0];
437
657
  if (!thread) return c.json({ error: "This session has no conversation to name yet." }, 409);
438
658
  const stored = await options.memorySettings.get({
439
659
  orgId: row.orgId,
@@ -448,7 +668,7 @@ function buildSourceControlSessionRoutes(options) {
448
668
  const title = await nameSession(sessionId, async () => {
449
669
  const generated = await options.controller.generateThreadTitle({
450
670
  threadId: thread.id,
451
- resourceId: sessionId,
671
+ sessionId,
452
672
  requestContext,
453
673
  ...stored?.observerModelId ? { model: titleModel(stored.observerModelId) } : {}
454
674
  });