@mastra/factory 0.10.0-alpha.2 → 0.10.0-alpha.8

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 (116) hide show
  1. package/CHANGELOG.md +112 -0
  2. package/dist/factory.d.ts +8 -0
  3. package/dist/factory.d.ts.map +1 -1
  4. package/dist/factory.js +24 -8
  5. package/dist/factory.js.map +1 -1
  6. package/dist/index.d.ts +2 -0
  7. package/dist/index.d.ts.map +1 -1
  8. package/dist/index.js +2 -1
  9. package/dist/integrations/github/integration.d.ts.map +1 -1
  10. package/dist/integrations/github/integration.js +1 -0
  11. package/dist/integrations/github/integration.js.map +1 -1
  12. package/dist/integrations/github/provenance.d.ts +7 -2
  13. package/dist/integrations/github/provenance.d.ts.map +1 -1
  14. package/dist/integrations/github/provenance.js +16 -2
  15. package/dist/integrations/github/provenance.js.map +1 -1
  16. package/dist/integrations/github/routes.d.ts +3 -0
  17. package/dist/integrations/github/routes.d.ts.map +1 -1
  18. package/dist/integrations/github/routes.js +75 -6
  19. package/dist/integrations/github/routes.js.map +1 -1
  20. package/dist/integrations/github/rules.d.ts.map +1 -1
  21. package/dist/integrations/github/rules.js +193 -127
  22. package/dist/integrations/github/rules.js.map +1 -1
  23. package/dist/integrations/platform/github/integration.d.ts.map +1 -1
  24. package/dist/integrations/platform/github/integration.js +1 -0
  25. package/dist/integrations/platform/github/integration.js.map +1 -1
  26. package/dist/routes/attention.d.ts +17 -0
  27. package/dist/routes/attention.d.ts.map +1 -0
  28. package/dist/routes/attention.js +305 -0
  29. package/dist/routes/attention.js.map +1 -0
  30. package/dist/routes/surface.d.ts +2 -3
  31. package/dist/routes/surface.d.ts.map +1 -1
  32. package/dist/routes/surface.js +61 -43
  33. package/dist/routes/surface.js.map +1 -1
  34. package/dist/routes/work-items.d.ts.map +1 -1
  35. package/dist/routes/work-items.js +35 -14
  36. package/dist/routes/work-items.js.map +1 -1
  37. package/dist/rules/defaults.js +5 -5
  38. package/dist/rules/defaults.js.map +1 -1
  39. package/dist/rules/dispatch-errors.d.ts +13 -0
  40. package/dist/rules/dispatch-errors.d.ts.map +1 -0
  41. package/dist/rules/dispatch-errors.js +77 -0
  42. package/dist/rules/dispatch-errors.js.map +1 -0
  43. package/dist/rules/dispatcher.d.ts +9 -0
  44. package/dist/rules/dispatcher.d.ts.map +1 -1
  45. package/dist/rules/dispatcher.js +118 -45
  46. package/dist/rules/dispatcher.js.map +1 -1
  47. package/dist/rules/processor.d.ts.map +1 -1
  48. package/dist/rules/processor.js +30 -14
  49. package/dist/rules/processor.js.map +1 -1
  50. package/dist/rules/terminal-cleanup.d.ts +1 -1
  51. package/dist/rules/terminal-cleanup.d.ts.map +1 -1
  52. package/dist/rules/terminal-cleanup.js +2 -2
  53. package/dist/rules/terminal-cleanup.js.map +1 -1
  54. package/dist/rules/transition-service.d.ts +2 -1
  55. package/dist/rules/transition-service.d.ts.map +1 -1
  56. package/dist/rules/transition-service.js +1 -1
  57. package/dist/rules/transition-service.js.map +1 -1
  58. package/dist/rules/types.d.ts +2 -0
  59. package/dist/rules/types.d.ts.map +1 -1
  60. package/dist/rules/types.js +9 -1
  61. package/dist/rules/types.js.map +1 -1
  62. package/dist/secret-encryption.d.ts +25 -0
  63. package/dist/secret-encryption.d.ts.map +1 -0
  64. package/dist/secret-encryption.js +96 -0
  65. package/dist/secret-encryption.js.map +1 -0
  66. package/dist/session/factory-session.d.ts +13 -3
  67. package/dist/session/factory-session.d.ts.map +1 -1
  68. package/dist/session/factory-session.js +15 -6
  69. package/dist/session/factory-session.js.map +1 -1
  70. package/dist/session/first-exec-capture.d.ts +16 -10
  71. package/dist/session/first-exec-capture.d.ts.map +1 -1
  72. package/dist/session/first-exec-capture.js +74 -14
  73. package/dist/session/first-exec-capture.js.map +1 -1
  74. package/dist/session/first-message-capture.d.ts +14 -10
  75. package/dist/session/first-message-capture.d.ts.map +1 -1
  76. package/dist/session/first-message-capture.js +17 -11
  77. package/dist/session/first-message-capture.js.map +1 -1
  78. package/dist/session/session-title.d.ts +7 -0
  79. package/dist/session/session-title.d.ts.map +1 -0
  80. package/dist/session/session-title.js +14 -0
  81. package/dist/session/session-title.js.map +1 -0
  82. package/dist/session/thread-title-mirror.d.ts +35 -0
  83. package/dist/session/thread-title-mirror.d.ts.map +1 -0
  84. package/dist/session/thread-title-mirror.js +51 -0
  85. package/dist/session/thread-title-mirror.js.map +1 -0
  86. package/dist/storage/domains/credentials/base.d.ts +3 -1
  87. package/dist/storage/domains/credentials/base.d.ts.map +1 -1
  88. package/dist/storage/domains/credentials/base.js +33 -15
  89. package/dist/storage/domains/credentials/base.js.map +1 -1
  90. package/dist/storage/domains/custom-providers/base.d.ts +3 -1
  91. package/dist/storage/domains/custom-providers/base.d.ts.map +1 -1
  92. package/dist/storage/domains/custom-providers/base.js +45 -25
  93. package/dist/storage/domains/custom-providers/base.js.map +1 -1
  94. package/dist/storage/domains/integrations/base.d.ts +3 -1
  95. package/dist/storage/domains/integrations/base.d.ts.map +1 -1
  96. package/dist/storage/domains/integrations/base.js +28 -12
  97. package/dist/storage/domains/integrations/base.js.map +1 -1
  98. package/dist/storage/domains/source-control/base.d.ts +8 -0
  99. package/dist/storage/domains/source-control/base.d.ts.map +1 -1
  100. package/dist/storage/domains/source-control/base.js +14 -2
  101. package/dist/storage/domains/source-control/base.js.map +1 -1
  102. package/dist/storage/domains/source-control/inmemory.d.ts +4 -0
  103. package/dist/storage/domains/source-control/inmemory.d.ts.map +1 -1
  104. package/dist/storage/domains/source-control/inmemory.js +7 -0
  105. package/dist/storage/domains/source-control/inmemory.js.map +1 -1
  106. package/dist/storage/domains/work-items/base.d.ts +115 -12
  107. package/dist/storage/domains/work-items/base.d.ts.map +1 -1
  108. package/dist/storage/domains/work-items/base.js +497 -43
  109. package/dist/storage/domains/work-items/base.js.map +1 -1
  110. package/dist/work-item-branch.d.ts +23 -0
  111. package/dist/work-item-branch.d.ts.map +1 -0
  112. package/dist/work-item-branch.js +39 -0
  113. package/dist/work-item-branch.js.map +1 -0
  114. package/factory-skills/factory-rereview/SKILL.md +2 -0
  115. package/factory-skills/factory-review/SKILL.md +2 -0
  116. package/package.json +7 -7
@@ -3,12 +3,15 @@ import { listPullRequestSubscriptionsForThread, subscribeToPullRequest } from ".
3
3
  import { SandboxBudgetError } from "../../sandbox/fleet.js";
4
4
  import { MaterializeError, WorktreeError, commitAll, ensureProjectSandbox, isValidGitRef as isValidGitRef$1, materializeRepo, pushBranch, teardownProjectSandbox } from "./sandbox.js";
5
5
  import { baseCheckpointIsStale } from "../../sandbox/base-checkpoint-triggers.js";
6
+ import { normalizeSessionTitle } from "../../session/session-title.js";
6
7
  import { getGithubFeatureDiagnostics, isGithubFeatureEnabled } from "./config.js";
7
8
  import { reclaimDeletedSessionSandbox } from "./sandbox-release.js";
8
9
  import { handleGithubWebhook } from "./webhook.js";
9
10
  import { registerApiRoute } from "@mastra/core/server";
10
11
  import { randomUUID } from "crypto";
11
12
  import { UniqueViolationError } from "@mastra/core/storage";
13
+ import { resolveModel } from "@mastra/code-sdk/agents/model";
14
+ import { RequestContext } from "@mastra/core/request-context";
12
15
  import { streamSSE } from "hono/streaming";
13
16
  //#region src/integrations/github/routes.ts
14
17
  /**
@@ -24,7 +27,6 @@ import { streamSSE } from "hono/streaming";
24
27
  * so the SPA can cleanly hide all GitHub UI.
25
28
  */
26
29
  const sessionOperationLocks = /* @__PURE__ */ new Map();
27
- const MAX_SESSION_TITLE_LENGTH = 80;
28
30
  const USER_SESSION_BRANCH_PREFIX = "user/session-";
29
31
  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}$/;
30
32
  /**
@@ -69,9 +71,6 @@ function isValidGitRef(value) {
69
71
  function isJsonObject(value) {
70
72
  return typeof value === "object" && value !== null && !Array.isArray(value);
71
73
  }
72
- function normalizeSessionTitle(title) {
73
- return [...title.replace(/\s+/g, " ").trim()].slice(0, MAX_SESSION_TITLE_LENGTH).join("").trimEnd() || null;
74
- }
75
74
  /**
76
75
  * Resolve the org-scoped tenant for a GitHub request. GitHub project features
77
76
  * are org-owned, so they require both a signed-in user and a WorkOS
@@ -208,7 +207,7 @@ async function ingestPolledEvents(events, ingestFactoryEvent) {
208
207
  */
209
208
  function buildGithubRoutes(options) {
210
209
  const routes = [];
211
- const { auth, fleet, storage, github, stateSigner, controller, emitAudit, sessionRetirement } = options;
210
+ const { auth, fleet, storage, github, stateSigner, controller, memorySettings, emitAudit, sessionRetirement } = options;
212
211
  const diagnostics = () => getGithubFeatureDiagnostics({
213
212
  github,
214
213
  auth,
@@ -688,6 +687,7 @@ function buildGithubRoutes(options) {
688
687
  auth,
689
688
  fleet,
690
689
  controller,
690
+ memorySettings,
691
691
  emitAudit,
692
692
  sessionRetirement
693
693
  }));
@@ -894,7 +894,33 @@ async function loadOwnedProject(options) {
894
894
  sandboxRow: await loadOrCreateSandboxRow(github, project, userId)
895
895
  };
896
896
  }
897
- function buildProjectGitRoutes({ github, auth, fleet, controller, emitAudit, sessionRetirement }) {
897
+ /**
898
+ * One naming per session at a time: a second caller joins the run already in
899
+ * flight instead of paying for another model call and racing its rename.
900
+ */
901
+ function createSessionNaming() {
902
+ const inFlight = /* @__PURE__ */ new Map();
903
+ return (sessionId, run) => {
904
+ const pending = inFlight.get(sessionId);
905
+ if (pending) return pending;
906
+ const started = run().finally(() => inFlight.delete(sessionId));
907
+ inFlight.set(sessionId, started);
908
+ return started;
909
+ };
910
+ }
911
+ /**
912
+ * Name a thread with a stored model id. Resolution has to go through
913
+ * mastracode's gateway: a bare id handed to core's model router looks for a
914
+ * process env key instead of the caller's stored provider credentials.
915
+ */
916
+ function titleModel(modelId) {
917
+ return ({ requestContext }) => resolveModel(modelId, {
918
+ remapForCodexOAuth: true,
919
+ requestContext
920
+ });
921
+ }
922
+ function buildProjectGitRoutes({ github, auth, fleet, controller, memorySettings, emitAudit, sessionRetirement }) {
923
+ const nameSession = createSessionNaming();
898
924
  return [
899
925
  registerApiRoute("/web/github/projects/:id/sessions", {
900
926
  method: "GET",
@@ -1029,6 +1055,49 @@ function buildProjectGitRoutes({ github, auth, fleet, controller, emitAudit, ses
1029
1055
  return c.json({ removed: true });
1030
1056
  }
1031
1057
  }),
1058
+ registerApiRoute("/web/user-sessions/:sessionId/title", {
1059
+ method: "POST",
1060
+ requiresAuth: false,
1061
+ handler: async (c) => {
1062
+ const resolved = await resolveOrgTenant(loose(c), auth);
1063
+ if ("response" in resolved) return resolved.response;
1064
+ const sessionId = c.req.param("sessionId");
1065
+ const row = await github.sourceControlStorage.sessions.getBySessionId(sessionId);
1066
+ if (!row || row.orgId !== resolved.tenant.orgId || row.userId !== resolved.tenant.userId) return c.json({ error: "Session not found" }, 404);
1067
+ if (!controller) return c.json({ error: "Sessions are not available on this server." }, 503);
1068
+ const thread = (await controller.queryThreads({ resourceId: sessionId })).sort((a, b) => b.updatedAt.getTime() - a.updatedAt.getTime())[0];
1069
+ if (!thread) return c.json({ error: "This session has no conversation to name yet." }, 409);
1070
+ const stored = await memorySettings.get({
1071
+ orgId: row.orgId,
1072
+ userId: row.userId
1073
+ });
1074
+ const requestContext = new RequestContext();
1075
+ requestContext.set("user", {
1076
+ workosId: row.userId,
1077
+ organizationId: row.orgId
1078
+ });
1079
+ try {
1080
+ const title = await nameSession(sessionId, async () => {
1081
+ const generated = await controller.generateThreadTitle({
1082
+ threadId: thread.id,
1083
+ resourceId: sessionId,
1084
+ requestContext,
1085
+ ...stored?.observerModelId ? { model: titleModel(stored.observerModelId) } : {}
1086
+ });
1087
+ const named = generated ? normalizeSessionTitle(generated) : null;
1088
+ if (named) await github.sourceControlStorage.sessions.rename({
1089
+ sessionId,
1090
+ title: named
1091
+ });
1092
+ return named;
1093
+ });
1094
+ if (!title) return c.json({ error: "The model returned an empty title. Try again." }, 502);
1095
+ return c.json({ title });
1096
+ } catch (error) {
1097
+ return c.json({ error: error instanceof Error ? error.message : String(error) }, 500);
1098
+ }
1099
+ }
1100
+ }),
1032
1101
  registerApiRoute("/web/github/projects/:id/commit", {
1033
1102
  method: "POST",
1034
1103
  requiresAuth: false,