@sentry/junior 0.162.0 → 0.164.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 (96) hide show
  1. package/README.md +2 -0
  2. package/dist/{agent-hooks-TL2SGC5W.js → agent-hooks-WTBPNRTC.js} +10 -10
  3. package/dist/api/acp/route.d.ts +13 -0
  4. package/dist/api/schema/workspace.d.ts +47 -0
  5. package/dist/api/schema.d.ts +2 -0
  6. package/dist/api/schema.js +15 -3
  7. package/dist/api/workspaces/routes.d.ts +4 -0
  8. package/dist/api.js +321 -408
  9. package/dist/app.d.ts +2 -2
  10. package/dist/app.js +482 -38
  11. package/dist/{catalog-runtime-IGSMIADJ.js → catalog-runtime-CZ2SQINY.js} +5 -5
  12. package/dist/chat/agent/sandbox.d.ts +4 -0
  13. package/dist/chat/api-turns/cancellation.d.ts +27 -0
  14. package/dist/chat/api-turns/routing.d.ts +31 -0
  15. package/dist/chat/api-turns/work.d.ts +12 -29
  16. package/dist/chat/app/conversation-work.d.ts +6 -1
  17. package/dist/chat/app/production.d.ts +2 -2
  18. package/dist/chat/conversations/history.d.ts +3 -0
  19. package/dist/chat/conversations/turn-lifecycle.d.ts +1 -1
  20. package/dist/chat/experimental.d.ts +1 -1
  21. package/dist/chat/plugins/agent-hooks.d.ts +4 -0
  22. package/dist/chat/repository-instructions.d.ts +1 -1
  23. package/dist/chat/sandbox/paths.d.ts +1 -0
  24. package/dist/chat/sandbox/prepare-workspace.d.ts +11 -0
  25. package/dist/chat/sandbox/ref.d.ts +1 -0
  26. package/dist/chat/sandbox/sandbox.d.ts +4 -0
  27. package/dist/chat/sandbox/session.d.ts +4 -0
  28. package/dist/chat/sandbox/snapshot/profile.d.ts +4 -3
  29. package/dist/chat/sandbox/snapshot/resolve.d.ts +4 -0
  30. package/dist/chat/sandbox/workspace.d.ts +4 -0
  31. package/dist/chat/tools/types.d.ts +5 -0
  32. package/dist/chat/workspaces/checkout-path.d.ts +4 -0
  33. package/dist/chat/workspaces/store.d.ts +37 -0
  34. package/dist/chat/workspaces/tools.d.ts +4 -0
  35. package/dist/chat/workspaces/types.d.ts +13 -0
  36. package/dist/chat/workspaces/validation.d.ts +21 -0
  37. package/dist/{chunk-THXMSSFZ.js → chunk-26JYGL2L.js} +1 -1
  38. package/dist/{chunk-OPNJRQDP.js → chunk-2K25MRZK.js} +9 -6
  39. package/dist/{chunk-C3KUKA27.js → chunk-3L23VTY7.js} +17 -17
  40. package/dist/{chunk-JJ3VXFDI.js → chunk-4GTOFUQF.js} +1 -1
  41. package/dist/{chunk-RDV4BQRZ.js → chunk-5FWQ73UZ.js} +1 -1
  42. package/dist/{chunk-BPZQWAZJ.js → chunk-5GLGQHO3.js} +4 -1
  43. package/dist/{chunk-K7IV6UV3.js → chunk-6BXV63YX.js} +5 -5
  44. package/dist/{chunk-4WYGQ47U.js → chunk-6ENAACWN.js} +5 -5
  45. package/dist/{chunk-EHQLTK3X.js → chunk-7WKWMMYQ.js} +323 -127
  46. package/dist/chunk-BVREIWBD.js +131 -0
  47. package/dist/{chunk-DZC3F2UI.js → chunk-BXBZDV3C.js} +1 -1
  48. package/dist/{chunk-HW4BW3PC.js → chunk-CGCNFEAU.js} +4 -4
  49. package/dist/{chunk-JRVURR3H.js → chunk-FKDY7NTC.js} +543 -164
  50. package/dist/{chunk-MNCEGXEH.js → chunk-FX4PX3SA.js} +2 -2
  51. package/dist/{chunk-OBFRMQBY.js → chunk-H36GJVJV.js} +9 -9
  52. package/dist/{chunk-V7QL4QMW.js → chunk-HHW6ZVIZ.js} +12 -7
  53. package/dist/{chunk-O6P7DZ6O.js → chunk-JW23XD4I.js} +6 -6
  54. package/dist/{chunk-DDQ43S5Q.js → chunk-LPLVNMVN.js} +4 -4
  55. package/dist/{chunk-5NEBOHRG.js → chunk-NAGI2XH3.js} +4 -4
  56. package/dist/{chunk-FEWT5KPP.js → chunk-NLTQRYNP.js} +2 -2
  57. package/dist/{chunk-SA6BEEAB.js → chunk-PU45BSBS.js} +108 -74
  58. package/dist/{chunk-7DTPFFQX.js → chunk-RBV4JHCP.js} +1 -1
  59. package/dist/{chunk-6BJFIWEV.js → chunk-RJHZNPDH.js} +46 -87
  60. package/dist/{chunk-FESUWAYU.js → chunk-RULIISEI.js} +1 -1
  61. package/dist/{chunk-MMBMDSRK.js → chunk-RYYEHWIL.js} +1 -1
  62. package/dist/{chunk-Y75ZDQB5.js → chunk-VHSEMJTS.js} +1 -1
  63. package/dist/{chunk-5IDFPCON.js → chunk-VRS6WDK5.js} +1 -1
  64. package/dist/{chunk-EBEHJPFF.js → chunk-VV2DN24T.js} +1 -1
  65. package/dist/{chunk-WHAJ3QVY.js → chunk-WJUKESU2.js} +1 -1
  66. package/dist/{chunk-H2KW7AZC.js → chunk-XAIRI54J.js} +1 -1
  67. package/dist/{chunk-AJ7J2HWY.js → chunk-Y2B6AXZQ.js} +6 -6
  68. package/dist/{chunk-QHCIZLIX.js → chunk-YHCTPDXS.js} +356 -13
  69. package/dist/{chunk-CZ6EHOU5.js → chunk-ZSNABC2E.js} +40 -2
  70. package/dist/{chunk-KQSO4DJ4.js → chunk-ZUTAGCPH.js} +9 -9
  71. package/dist/cli/chat.js +32 -32
  72. package/dist/cli/check.js +6 -6
  73. package/dist/cli/plugins.js +13 -13
  74. package/dist/cli/snapshot-create.js +10 -10
  75. package/dist/cli/upgrade.js +7 -7
  76. package/dist/db/schema/workspaces.d.ts +169 -0
  77. package/dist/db/schema.d.ts +169 -1
  78. package/dist/{db-66XZ4HHQ.js → db-32KRFS6L.js} +7 -7
  79. package/dist/{experimental-HH6OM6UH.js → experimental-XVDOSRBS.js} +1 -1
  80. package/dist/instrumentation.js +4 -4
  81. package/dist/nitro.js +2 -2
  82. package/dist/{oauth-callback-server-FMLKDUUF.js → oauth-callback-server-CGZP2Z6U.js} +24 -24
  83. package/dist/{runner-YZONUMNY.js → runner-S5N4Q2XL.js} +32 -34
  84. package/dist/{skills-3UDJJXSO.js → skills-KYPSHSQR.js} +6 -6
  85. package/dist/spawn-EGOB3CLV.js +37 -0
  86. package/dist/{validation-3HTDBONC.js → validation-SZBE7JNF.js} +6 -6
  87. package/dist/version.js +1 -1
  88. package/dist/{work-O4YTIS54.js → work-GCZKHEZX.js} +18 -18
  89. package/dist/worker-6MY5Q4A2.js +24 -0
  90. package/migrations/0029_dizzy_barracuda.sql +19 -0
  91. package/migrations/meta/0029_snapshot.json +2709 -0
  92. package/migrations/meta/_journal.json +8 -1
  93. package/package.json +7 -4
  94. package/dist/chunk-EM225ITJ.js +0 -56
  95. package/dist/spawn-TBPVA5S2.js +0 -37
  96. package/dist/worker-WHURUEYX.js +0 -24
package/dist/api.js CHANGED
@@ -23,6 +23,7 @@ import {
23
23
  createConversationMessageBodySchema,
24
24
  createPersonalTokenBodySchema,
25
25
  createdPersonalTokenSchema,
26
+ deleteWorkspaceResponseSchema,
26
27
  locationDetailReportSchema,
27
28
  locationDirectoryReportSchema,
28
29
  locationParamsSchema,
@@ -35,26 +36,38 @@ import {
35
36
  taskExecutionListSchema,
36
37
  taskListSchema,
37
38
  taskParamsSchema,
38
- taskRunListSchema
39
- } from "./chunk-SA6BEEAB.js";
39
+ taskRunListSchema,
40
+ workspaceBodySchema,
41
+ workspaceListSchema,
42
+ workspaceParamsSchema,
43
+ workspaceSchema
44
+ } from "./chunk-PU45BSBS.js";
40
45
  import {
41
46
  appendAndEnqueueApiConversationMessage,
47
+ authenticatePersonalToken,
48
+ conversationHasParticipantEmail,
49
+ conversationHasParticipantUser,
42
50
  createAndEnqueueApiConversation,
51
+ createPersonalToken,
43
52
  createVercelAttachmentStorage,
44
53
  formatSlackConversationRedactedLabel,
54
+ listPersonalTokens,
45
55
  lookupSlackUser,
56
+ readConversationAccessFromSql,
46
57
  readHealthReport,
47
58
  resolveSlackConversationContextFromThreadId,
59
+ revokePersonalToken,
60
+ viewerConversationMembership,
48
61
  webActorFromEmail
49
- } from "./chunk-JRVURR3H.js";
62
+ } from "./chunk-FKDY7NTC.js";
50
63
  import {
51
64
  buildSentryConversationUrl,
52
65
  getWebAuthorization
53
- } from "./chunk-RDV4BQRZ.js";
66
+ } from "./chunk-5FWQ73UZ.js";
54
67
  import {
55
68
  cancelHumanFacingPendingMessages,
56
69
  getConversation
57
- } from "./chunk-5NEBOHRG.js";
70
+ } from "./chunk-NAGI2XH3.js";
58
71
  import {
59
72
  readTaskExecutionByConversationId,
60
73
  readTaskExecutionDays,
@@ -62,8 +75,8 @@ import {
62
75
  readTaskExecutionSummaries,
63
76
  readTaskExecutions,
64
77
  readTaskRuns
65
- } from "./chunk-KQSO4DJ4.js";
66
- import "./chunk-OPNJRQDP.js";
78
+ } from "./chunk-ZUTAGCPH.js";
79
+ import "./chunk-2K25MRZK.js";
67
80
  import {
68
81
  healthReportSchema,
69
82
  pluginOperationalReportFeedSchema,
@@ -88,30 +101,37 @@ import {
88
101
  listPublicScheduledTasksForTeams,
89
102
  readLiveAttachment,
90
103
  readStats
91
- } from "./chunk-4WYGQ47U.js";
104
+ } from "./chunk-6ENAACWN.js";
92
105
  import {
93
106
  parseSlackThreadId
94
- } from "./chunk-WHAJ3QVY.js";
107
+ } from "./chunk-WJUKESU2.js";
95
108
  import {
96
109
  agentTurnUsageSchema,
97
110
  fallbackShortTitle,
98
111
  hasAgentTurnUsage,
99
112
  renderJuniorNativeConversationEvent
100
- } from "./chunk-V7QL4QMW.js";
113
+ } from "./chunk-HHW6ZVIZ.js";
101
114
  import "./chunk-3Y47VMHV.js";
102
115
  import "./chunk-PDO5BLNM.js";
103
116
  import {
117
+ WorkspaceValidationError,
104
118
  createPluginLogger,
119
+ createWorkspace,
120
+ deleteWorkspace,
105
121
  findUserByEmail,
106
122
  getPlugins,
107
123
  getSlackClient,
124
+ getWorkspace,
108
125
  listConversationAnnotations,
109
126
  listConversationAnnotationsById,
127
+ listWorkspaces,
110
128
  renderPluginConversationEvent,
111
129
  resolveViewerUser,
112
130
  updateViewerDisplayName,
113
- withSlackRetries
114
- } from "./chunk-QHCIZLIX.js";
131
+ updateWorkspace,
132
+ withSlackRetries,
133
+ workspaceRepoCheckoutPath
134
+ } from "./chunk-YHCTPDXS.js";
115
135
  import {
116
136
  decodeStoredConversationEvent,
117
137
  getConversationStore,
@@ -119,24 +139,20 @@ import {
119
139
  getSqlExecutor,
120
140
  locationFromRow,
121
141
  parseSessionSource
122
- } from "./chunk-DDQ43S5Q.js";
142
+ } from "./chunk-LPLVNMVN.js";
123
143
  import {
124
- juniorApiTokens,
125
144
  juniorConversationEvents,
126
- juniorConversationParticipants,
127
145
  juniorConversations,
128
146
  juniorIdentities,
129
147
  juniorUsers
130
- } from "./chunk-CZ6EHOU5.js";
131
- import "./chunk-EM225ITJ.js";
132
- import "./chunk-DZC3F2UI.js";
133
- import "./chunk-MNCEGXEH.js";
148
+ } from "./chunk-ZSNABC2E.js";
149
+ import "./chunk-BVREIWBD.js";
150
+ import "./chunk-BXBZDV3C.js";
151
+ import "./chunk-FX4PX3SA.js";
134
152
  import {
135
153
  juniorDestinations
136
154
  } from "./chunk-VFUK3X5B.js";
137
- import {
138
- canExposeConversationPayload
139
- } from "./chunk-7DTPFFQX.js";
155
+ import "./chunk-RBV4JHCP.js";
140
156
  import "./chunk-BDUENQD3.js";
141
157
  import {
142
158
  parseSlackChannelId,
@@ -146,14 +162,14 @@ import {
146
162
  import {
147
163
  logException,
148
164
  logWarn
149
- } from "./chunk-Y75ZDQB5.js";
165
+ } from "./chunk-VHSEMJTS.js";
150
166
  import "./chunk-6GWA276C.js";
151
- import "./chunk-THXMSSFZ.js";
152
- import "./chunk-BPZQWAZJ.js";
167
+ import "./chunk-26JYGL2L.js";
168
+ import "./chunk-5GLGQHO3.js";
153
169
  import "./chunk-MLKGABMK.js";
154
170
 
155
171
  // src/api.ts
156
- import { Hono as Hono7 } from "hono";
172
+ import { Hono as Hono8 } from "hono";
157
173
  import { HTTPException as HTTPException2 } from "hono/http-exception";
158
174
 
159
175
  // src/api/conversations/routes.ts
@@ -233,132 +249,6 @@ async function archiveConversation(conversationId, body) {
233
249
  return { archived: body.archived };
234
250
  }
235
251
 
236
- // src/api/conversations/access.ts
237
- import { eq as eq3, inArray as inArray2 } from "drizzle-orm";
238
- import { alias } from "drizzle-orm/pg-core";
239
-
240
- // src/api/conversations/membership.ts
241
- import { and as and2, eq as eq2, exists, inArray, or } from "drizzle-orm";
242
- function conversationHasParticipantUser(userId) {
243
- const participant = getDb().select({
244
- rootConversationId: juniorConversationParticipants.rootConversationId
245
- }).from(juniorConversationParticipants).where(
246
- and2(
247
- eq2(
248
- juniorConversationParticipants.rootConversationId,
249
- juniorConversations.conversationId
250
- ),
251
- eq2(juniorConversationParticipants.userId, userId)
252
- )
253
- );
254
- return exists(participant);
255
- }
256
- function conversationHasParticipantEmail(email) {
257
- const participant = getDb().select({
258
- rootConversationId: juniorConversationParticipants.rootConversationId
259
- }).from(juniorConversationParticipants).innerJoin(
260
- juniorUsers,
261
- eq2(juniorUsers.id, juniorConversationParticipants.userId)
262
- ).where(
263
- and2(
264
- eq2(
265
- juniorConversationParticipants.rootConversationId,
266
- juniorConversations.conversationId
267
- ),
268
- eq2(juniorUsers.primaryEmailNormalized, email)
269
- )
270
- );
271
- return exists(participant);
272
- }
273
- function viewerConversationMembership(args) {
274
- if (args.actorMatch && args.participantMatch) {
275
- return or(args.actorMatch, args.participantMatch);
276
- }
277
- return args.actorMatch ?? args.participantMatch;
278
- }
279
- async function conversationIdsWithParticipantUser(db, conversationIds, userId) {
280
- if (conversationIds.length === 0) {
281
- return /* @__PURE__ */ new Set();
282
- }
283
- const rows = await db.select({
284
- rootConversationId: juniorConversationParticipants.rootConversationId
285
- }).from(juniorConversationParticipants).where(
286
- and2(
287
- eq2(juniorConversationParticipants.userId, userId),
288
- inArray(juniorConversationParticipants.rootConversationId, [
289
- ...conversationIds
290
- ])
291
- )
292
- );
293
- return new Set(rows.map((row) => row.rootConversationId));
294
- }
295
-
296
- // src/api/conversations/access.ts
297
- var rootConversation = alias(juniorConversations, "access_root_conversation");
298
- var rootDestination = alias(juniorDestinations, "access_root_destination");
299
- var rootIdentity = alias(juniorIdentities, "access_root_identity");
300
- async function readConversationAccessFromSql(db, conversationIds, viewer) {
301
- if (conversationIds.length === 0) return /* @__PURE__ */ new Map();
302
- const normalizedViewerEmail = viewer?.email.trim().toLowerCase() || void 0;
303
- const rows = await db.select({
304
- conversationId: juniorConversations.conversationId,
305
- parentConversationId: juniorConversations.parentConversationId,
306
- storedRootConversationId: juniorConversations.rootConversationId,
307
- rootConversationId: rootConversation.conversationId,
308
- rootParentConversationId: rootConversation.parentConversationId,
309
- rootRootConversationId: rootConversation.rootConversationId,
310
- visibility: rootDestination.visibility,
311
- rootEmailNormalized: rootIdentity.emailNormalized,
312
- rootEmailVerified: rootIdentity.emailVerified,
313
- rootUserId: rootIdentity.userId
314
- }).from(juniorConversations).leftJoin(
315
- rootConversation,
316
- eq3(
317
- rootConversation.conversationId,
318
- juniorConversations.rootConversationId
319
- )
320
- ).leftJoin(
321
- rootDestination,
322
- eq3(rootDestination.id, rootConversation.destinationId)
323
- ).leftJoin(
324
- rootIdentity,
325
- eq3(rootIdentity.id, rootConversation.actorIdentityId)
326
- ).where(inArray2(juniorConversations.conversationId, [...conversationIds]));
327
- const membershipConversationIds = /* @__PURE__ */ new Set();
328
- for (const row of rows) {
329
- membershipConversationIds.add(row.conversationId);
330
- if (row.storedRootConversationId) {
331
- membershipConversationIds.add(row.storedRootConversationId);
332
- }
333
- }
334
- const participantRootIds = viewer !== void 0 ? await conversationIdsWithParticipantUser(
335
- db,
336
- [...membershipConversationIds],
337
- viewer.id
338
- ) : /* @__PURE__ */ new Set();
339
- return new Map(
340
- rows.map((row) => {
341
- const hasValidRoot = row.rootConversationId !== null && row.rootConversationId === row.storedRootConversationId && row.rootRootConversationId === row.rootConversationId && row.rootParentConversationId === null && (row.parentConversationId !== null || row.storedRootConversationId === row.conversationId);
342
- const validRootConversationId = hasValidRoot ? row.rootConversationId ?? void 0 : void 0;
343
- const visibility = validRootConversationId === void 0 ? null : row.visibility;
344
- const isRootActor = validRootConversationId !== void 0 && viewer !== void 0 && (row.rootUserId === viewer.id || normalizedViewerEmail !== void 0 && row.rootEmailVerified === true && row.rootEmailNormalized === normalizedViewerEmail);
345
- const isMaterializedParticipant = participantRootIds.has(row.conversationId) || validRootConversationId !== void 0 && participantRootIds.has(validRootConversationId);
346
- const isParticipant = isRootActor || isMaterializedParticipant;
347
- const canViewPrivateContent = isParticipant || validRootConversationId !== void 0 && canExposeConversationPayload({
348
- visibility: visibility ?? void 0
349
- });
350
- return [
351
- row.conversationId,
352
- {
353
- canViewPrivateContent,
354
- isParticipant,
355
- visibility
356
- }
357
- ];
358
- })
359
- );
360
- }
361
-
362
252
  // src/api/conversations/attachments.ts
363
253
  function mayDisplayInline(contentType) {
364
254
  return contentType === "image/gif" || contentType === "image/jpeg" || contentType === "image/png" || contentType === "image/webp";
@@ -579,7 +469,7 @@ async function resolveSlackTeamDomains(teamIds) {
579
469
  }
580
470
 
581
471
  // src/chat/pi/sql-model-usage.ts
582
- import { and as and3, eq as eq4, sql } from "drizzle-orm";
472
+ import { and as and2, eq as eq2, sql } from "drizzle-orm";
583
473
  var message = sql`${juniorConversationEvents.payload}`;
584
474
  var usage = sql`${message}->'usage'`;
585
475
  var cost = sql`${usage}->'cost'`;
@@ -677,14 +567,14 @@ async function readConversationModelUsageFromSql(executor, options) {
677
567
  costTotal: summedCost(nonnegativeNumber(cost, "total"))
678
568
  }).from(juniorConversationEvents).innerJoin(
679
569
  juniorConversations,
680
- eq4(
570
+ eq2(
681
571
  juniorConversations.conversationId,
682
572
  juniorConversationEvents.conversationId
683
573
  )
684
574
  ).where(
685
- and3(
686
- options.includeDescendants ? eq4(juniorConversations.rootConversationId, options.conversationId) : eq4(juniorConversationEvents.conversationId, options.conversationId),
687
- eq4(juniorConversationEvents.type, "assistant_message"),
575
+ and2(
576
+ options.includeDescendants ? eq2(juniorConversations.rootConversationId, options.conversationId) : eq2(juniorConversationEvents.conversationId, options.conversationId),
577
+ eq2(juniorConversationEvents.type, "assistant_message"),
688
578
  sql`jsonb_typeof(${message}->'provider') = 'string'`,
689
579
  sql`jsonb_typeof(${message}->'model') = 'string'`,
690
580
  sql`coalesce(${message}->>'provider', '') <> ''`,
@@ -746,12 +636,12 @@ function decodeConversationCursor(args) {
746
636
 
747
637
  // src/api/conversations/event-page.ts
748
638
  import {
749
- and as and4,
639
+ and as and3,
750
640
  asc,
751
641
  desc,
752
- eq as eq5,
642
+ eq as eq3,
753
643
  getTableColumns,
754
- inArray as inArray3,
644
+ inArray,
755
645
  lt,
756
646
  sql as sql2
757
647
  } from "drizzle-orm";
@@ -1174,18 +1064,18 @@ async function readConversationEventRows(executor, args) {
1174
1064
  else ${juniorConversationEvents.payload}
1175
1065
  end`
1176
1066
  }).from(juniorConversationEvents).where(
1177
- and4(
1178
- eq5(juniorConversationEvents.conversationId, args.conversationId),
1067
+ and3(
1068
+ eq3(juniorConversationEvents.conversationId, args.conversationId),
1179
1069
  args.beforeSeq === void 0 ? void 0 : lt(juniorConversationEvents.seq, args.beforeSeq),
1180
- inArray3(
1070
+ inArray(
1181
1071
  juniorConversationEvents.type,
1182
1072
  args.types ?? [...conversationReportSourceEventTypes]
1183
1073
  ),
1184
- args.subagentInvocationIds === void 0 ? void 0 : inArray3(
1074
+ args.subagentInvocationIds === void 0 ? void 0 : inArray(
1185
1075
  sql2`${juniorConversationEvents.payload}->>'subagentInvocationId'`,
1186
1076
  args.subagentInvocationIds
1187
1077
  ),
1188
- args.toolCallIds === void 0 ? void 0 : inArray3(
1078
+ args.toolCallIds === void 0 ? void 0 : inArray(
1189
1079
  sql2`${juniorConversationEvents.payload}->>'toolCallId'`,
1190
1080
  args.toolCallIds
1191
1081
  )
@@ -1266,7 +1156,7 @@ async function readConversationEventPage(executor, args) {
1266
1156
  }
1267
1157
 
1268
1158
  // src/api/conversations/list.ts
1269
- import { and as and8, asc as asc2, desc as desc2, eq as eq9, isNull as isNull3 } from "drizzle-orm";
1159
+ import { and as and7, asc as asc2, desc as desc2, eq as eq7, isNull as isNull3 } from "drizzle-orm";
1270
1160
 
1271
1161
  // src/api/conversations/shared.ts
1272
1162
  function slackStatsLocationLabel(input) {
@@ -1449,10 +1339,10 @@ function conversationSummaryFromStoredConversation(args) {
1449
1339
  }
1450
1340
 
1451
1341
  // src/api/conversations/usage.ts
1452
- import { and as and5, eq as eq6, inArray as inArray4, isNull, sql as sql3 } from "drizzle-orm";
1453
- import { alias as alias2 } from "drizzle-orm/pg-core";
1342
+ import { and as and4, eq as eq4, inArray as inArray2, isNull, sql as sql3 } from "drizzle-orm";
1343
+ import { alias } from "drizzle-orm/pg-core";
1454
1344
  var usage2 = juniorConversations.usage;
1455
- var metricRootConversation = alias2(
1345
+ var metricRootConversation = alias(
1456
1346
  juniorConversations,
1457
1347
  "metric_root_conversation"
1458
1348
  );
@@ -1523,19 +1413,19 @@ async function readRootConversationMetricsFromSql(db, rootConversationIds) {
1523
1413
  costTotal: summedCostNumber("total")
1524
1414
  }).from(juniorConversations).innerJoin(
1525
1415
  metricRootConversation,
1526
- and5(
1527
- eq6(
1416
+ and4(
1417
+ eq4(
1528
1418
  metricRootConversation.conversationId,
1529
1419
  juniorConversations.rootConversationId
1530
1420
  ),
1531
1421
  isNull(metricRootConversation.parentConversationId),
1532
- eq6(
1422
+ eq4(
1533
1423
  metricRootConversation.rootConversationId,
1534
1424
  metricRootConversation.conversationId
1535
1425
  )
1536
1426
  )
1537
1427
  ).where(
1538
- inArray4(juniorConversations.rootConversationId, [...rootConversationIds])
1428
+ inArray2(juniorConversations.rootConversationId, [...rootConversationIds])
1539
1429
  ).groupBy(juniorConversations.rootConversationId);
1540
1430
  return new Map(
1541
1431
  rows.flatMap((row) => {
@@ -1553,16 +1443,16 @@ async function readRootConversationMetricsFromSql(db, rootConversationIds) {
1553
1443
 
1554
1444
  // src/api/conversations/auxiliary-costs.ts
1555
1445
  import {
1556
- and as and6,
1557
- eq as eq7,
1558
- inArray as inArray5,
1446
+ and as and5,
1447
+ eq as eq5,
1448
+ inArray as inArray3,
1559
1449
  isNotNull as isNotNull2,
1560
1450
  isNull as isNull2,
1561
- or as or2,
1451
+ or,
1562
1452
  sql as sql4
1563
1453
  } from "drizzle-orm";
1564
- import { alias as alias3 } from "drizzle-orm/pg-core";
1565
- var auxiliaryRootConversation = alias3(
1454
+ import { alias as alias2 } from "drizzle-orm/pg-core";
1455
+ var auxiliaryRootConversation = alias2(
1566
1456
  juniorConversations,
1567
1457
  "auxiliary_root_conversation"
1568
1458
  );
@@ -1595,13 +1485,13 @@ async function readConversationAuxiliaryCostsFromSql(db, conversationIds, option
1595
1485
  ELSE ${juniorConversationEvents.type}
1596
1486
  END`;
1597
1487
  const cost2 = eventCost();
1598
- const selectedConversation = options.includeDescendants ? or2(
1599
- and6(
1600
- inArray5(juniorConversations.rootConversationId, selectedIds),
1488
+ const selectedConversation = options.includeDescendants ? or(
1489
+ and5(
1490
+ inArray3(juniorConversations.rootConversationId, selectedIds),
1601
1491
  isNotNull2(auxiliaryRootConversation.conversationId)
1602
1492
  ),
1603
- inArray5(juniorConversations.conversationId, selectedIds)
1604
- ) : inArray5(juniorConversations.conversationId, selectedIds);
1493
+ inArray3(juniorConversations.conversationId, selectedIds)
1494
+ ) : inArray3(juniorConversations.conversationId, selectedIds);
1605
1495
  const rows = await db.select({
1606
1496
  conversationId,
1607
1497
  costUsd: sql4`round(sum(${cost2}), 12)::double precision`.mapWith(
@@ -1612,29 +1502,29 @@ async function readConversationAuxiliaryCostsFromSql(db, conversationIds, option
1612
1502
  namespace
1613
1503
  }).from(juniorConversationEvents).innerJoin(
1614
1504
  juniorConversations,
1615
- eq7(
1505
+ eq5(
1616
1506
  juniorConversations.conversationId,
1617
1507
  juniorConversationEvents.conversationId
1618
1508
  )
1619
1509
  ).leftJoin(
1620
1510
  auxiliaryRootConversation,
1621
- and6(
1622
- eq7(
1511
+ and5(
1512
+ eq5(
1623
1513
  auxiliaryRootConversation.conversationId,
1624
1514
  juniorConversations.rootConversationId
1625
1515
  ),
1626
1516
  isNull2(auxiliaryRootConversation.parentConversationId),
1627
- eq7(
1517
+ eq5(
1628
1518
  auxiliaryRootConversation.rootConversationId,
1629
1519
  auxiliaryRootConversation.conversationId
1630
1520
  )
1631
1521
  )
1632
1522
  ).where(
1633
- and6(
1523
+ and5(
1634
1524
  selectedConversation,
1635
- or2(
1636
- eq7(juniorConversationEvents.type, "structured_event"),
1637
- inArray5(juniorConversationEvents.type, [
1525
+ or(
1526
+ eq5(juniorConversationEvents.type, "structured_event"),
1527
+ inArray3(juniorConversationEvents.type, [
1638
1528
  "guardian_action_reviewed",
1639
1529
  "turn_routed"
1640
1530
  ])
@@ -1786,7 +1676,7 @@ function isConversationPriority(conversation, nowMs) {
1786
1676
  }
1787
1677
 
1788
1678
  // src/api/conversations/user-message-activity.ts
1789
- import { and as and7, eq as eq8, inArray as inArray6, isNotNull as isNotNull3, or as or3, sql as sql5 } from "drizzle-orm";
1679
+ import { and as and6, eq as eq6, inArray as inArray4, isNotNull as isNotNull3, or as or2, sql as sql5 } from "drizzle-orm";
1790
1680
  async function readLastUserMessageAtByConversation(db, conversationIds) {
1791
1681
  if (conversationIds.length === 0) return /* @__PURE__ */ new Map();
1792
1682
  const authority = sql5`${juniorConversationEvents.payload}->'provenance'->>'authority'`;
@@ -1796,17 +1686,17 @@ async function readLastUserMessageAtByConversation(db, conversationIds) {
1796
1686
  conversationId: juniorConversationEvents.conversationId,
1797
1687
  lastUserMessageAt: sql5`max(${juniorConversationEvents.createdAt})`
1798
1688
  }).from(juniorConversationEvents).where(
1799
- and7(
1800
- inArray6(juniorConversationEvents.conversationId, conversationIds),
1801
- or3(
1802
- and7(
1803
- eq8(juniorConversationEvents.type, "user_message"),
1804
- eq8(authority, "instruction"),
1689
+ and6(
1690
+ inArray4(juniorConversationEvents.conversationId, conversationIds),
1691
+ or2(
1692
+ and6(
1693
+ eq6(juniorConversationEvents.type, "user_message"),
1694
+ eq6(authority, "instruction"),
1805
1695
  sql5`${actorPlatform} in ('slack', 'local', 'web')`
1806
1696
  ),
1807
- and7(
1808
- eq8(juniorConversationEvents.type, "message"),
1809
- eq8(role, "user"),
1697
+ and6(
1698
+ eq6(juniorConversationEvents.type, "message"),
1699
+ eq6(role, "user"),
1810
1700
  isNotNull3(juniorConversationEvents.actorIdentityId)
1811
1701
  )
1812
1702
  )
@@ -1826,12 +1716,12 @@ function conversationFeedMembershipFilter(filter) {
1826
1716
  if (!filter) return void 0;
1827
1717
  if (filter.kind === "viewer") {
1828
1718
  return viewerConversationMembership({
1829
- actorMatch: eq9(juniorIdentities.userId, filter.userId),
1719
+ actorMatch: eq7(juniorIdentities.userId, filter.userId),
1830
1720
  participantMatch: conversationHasParticipantUser(filter.userId)
1831
1721
  });
1832
1722
  }
1833
1723
  return viewerConversationMembership({
1834
- actorMatch: eq9(juniorUsers.primaryEmailNormalized, filter.email),
1724
+ actorMatch: eq7(juniorUsers.primaryEmailNormalized, filter.email),
1835
1725
  participantMatch: conversationHasParticipantEmail(filter.email)
1836
1726
  });
1837
1727
  }
@@ -1848,12 +1738,12 @@ async function conversationRows(db, limit, filter) {
1848
1738
  userDisplayName: juniorUsers.displayName
1849
1739
  }).from(juniorConversations).leftJoin(
1850
1740
  juniorDestinations,
1851
- eq9(juniorDestinations.id, juniorConversations.destinationId)
1741
+ eq7(juniorDestinations.id, juniorConversations.destinationId)
1852
1742
  ).leftJoin(
1853
1743
  juniorIdentities,
1854
- eq9(juniorIdentities.id, juniorConversations.actorIdentityId)
1855
- ).leftJoin(juniorUsers, eq9(juniorUsers.id, juniorIdentities.userId)).where(
1856
- and8(
1744
+ eq7(juniorIdentities.id, juniorConversations.actorIdentityId)
1745
+ ).leftJoin(juniorUsers, eq7(juniorUsers.id, juniorIdentities.userId)).where(
1746
+ and7(
1857
1747
  isNull3(juniorConversations.parentConversationId),
1858
1748
  isNull3(juniorConversations.archivedAt),
1859
1749
  conversationFeedMembershipFilter(filter)
@@ -1914,11 +1804,11 @@ async function readConversationRecordFromSql(conversationId) {
1914
1804
  userDisplayName: juniorUsers.displayName
1915
1805
  }).from(juniorConversations).leftJoin(
1916
1806
  juniorDestinations,
1917
- eq9(juniorDestinations.id, juniorConversations.destinationId)
1807
+ eq7(juniorDestinations.id, juniorConversations.destinationId)
1918
1808
  ).leftJoin(
1919
1809
  juniorIdentities,
1920
- eq9(juniorIdentities.id, juniorConversations.actorIdentityId)
1921
- ).leftJoin(juniorUsers, eq9(juniorUsers.id, juniorIdentities.userId)).where(eq9(juniorConversations.conversationId, conversationId)).limit(1);
1810
+ eq7(juniorIdentities.id, juniorConversations.actorIdentityId)
1811
+ ).leftJoin(juniorUsers, eq7(juniorUsers.id, juniorIdentities.userId)).where(eq7(juniorConversations.conversationId, conversationId)).limit(1);
1922
1812
  const row = rows[0];
1923
1813
  return row ? {
1924
1814
  conversation: conversationFromRow(row),
@@ -2042,7 +1932,7 @@ async function readConversationFeed(options = {}) {
2042
1932
  }
2043
1933
 
2044
1934
  // src/chat/tasks/read.ts
2045
- import { and as and9, eq as eq10, or as or4 } from "drizzle-orm";
1935
+ import { and as and8, eq as eq8, or as or3 } from "drizzle-orm";
2046
1936
 
2047
1937
  // src/chat/scheduled-tasks/personal.ts
2048
1938
  import { z as z3 } from "zod";
@@ -2152,16 +2042,16 @@ async function creatorProfileEmails(candidates) {
2152
2042
  email: juniorUsers.primaryEmailNormalized,
2153
2043
  slackUserId: juniorIdentities.providerSubjectId,
2154
2044
  teamId: juniorIdentities.providerTenantId
2155
- }).from(juniorIdentities).innerJoin(juniorUsers, eq10(juniorUsers.id, juniorIdentities.userId)).where(
2156
- and9(
2157
- eq10(juniorIdentities.kind, "user"),
2158
- eq10(juniorIdentities.provider, "slack"),
2159
- eq10(juniorIdentities.emailVerified, true),
2160
- or4(
2045
+ }).from(juniorIdentities).innerJoin(juniorUsers, eq8(juniorUsers.id, juniorIdentities.userId)).where(
2046
+ and8(
2047
+ eq8(juniorIdentities.kind, "user"),
2048
+ eq8(juniorIdentities.provider, "slack"),
2049
+ eq8(juniorIdentities.emailVerified, true),
2050
+ or3(
2161
2051
  ...[...selectors.values()].map(
2162
- (selector) => and9(
2163
- eq10(juniorIdentities.providerTenantId, selector.teamId),
2164
- eq10(juniorIdentities.providerSubjectId, selector.slackUserId)
2052
+ (selector) => and8(
2053
+ eq8(juniorIdentities.providerTenantId, selector.teamId),
2054
+ eq8(juniorIdentities.providerSubjectId, selector.slackUserId)
2165
2055
  )
2166
2056
  )
2167
2057
  )
@@ -2197,12 +2087,12 @@ async function destinationDetails(destinations) {
2197
2087
  providerTenantId: juniorDestinations.providerTenantId,
2198
2088
  visibility: juniorDestinations.visibility
2199
2089
  }).from(juniorDestinations).where(
2200
- or4(
2090
+ or3(
2201
2091
  ...[...selectors.values()].map(
2202
- (destination) => and9(
2203
- eq10(juniorDestinations.provider, "slack"),
2204
- eq10(juniorDestinations.providerTenantId, destination.teamId),
2205
- eq10(juniorDestinations.providerDestinationId, destination.channelId)
2092
+ (destination) => and8(
2093
+ eq8(juniorDestinations.provider, "slack"),
2094
+ eq8(juniorDestinations.providerTenantId, destination.teamId),
2095
+ eq8(juniorDestinations.providerDestinationId, destination.channelId)
2206
2096
  )
2207
2097
  )
2208
2098
  )
@@ -2767,19 +2657,19 @@ var slackMailboxMetadataSchema = z4.object({
2767
2657
  function isoFromMs(value) {
2768
2658
  return new Date(value).toISOString();
2769
2659
  }
2770
- function actorIdentityFromApiMetadata(metadata2) {
2660
+ function actorIdentityFromApiMetadata(metadata) {
2771
2661
  return {
2772
- email: metadata2.authorEmail.trim().toLowerCase(),
2773
- ...metadata2.authorFullName ? { fullName: metadata2.authorFullName } : {}
2662
+ email: metadata.authorEmail.trim().toLowerCase(),
2663
+ ...metadata.authorFullName ? { fullName: metadata.authorFullName } : {}
2774
2664
  };
2775
2665
  }
2776
- async function actorIdentityFromSlackMetadata(metadata2, teamId) {
2777
- if (metadata2.message.author.isMe === true) return void 0;
2778
- const slackUserId = metadata2.message.author.userId.trim();
2666
+ async function actorIdentityFromSlackMetadata(metadata, teamId) {
2667
+ if (metadata.message.author.isMe === true) return void 0;
2668
+ const slackUserId = metadata.message.author.userId.trim();
2779
2669
  if (!slackUserId) return void 0;
2780
2670
  const profile = teamId ? await lookupSlackUser(teamId, slackUserId) : null;
2781
- const slackUserName = profile?.userName?.trim() || metadata2.message.author.userName?.trim();
2782
- const fullName = profile?.fullName?.trim() || metadata2.message.author.fullName?.trim();
2671
+ const slackUserName = profile?.userName?.trim() || metadata.message.author.userName?.trim();
2672
+ const fullName = profile?.fullName?.trim() || metadata.message.author.fullName?.trim();
2783
2673
  const email = profile?.email?.trim().toLowerCase();
2784
2674
  return {
2785
2675
  slackUserId,
@@ -2790,32 +2680,32 @@ async function actorIdentityFromSlackMetadata(metadata2, teamId) {
2790
2680
  }
2791
2681
  async function projectPendingMessage(message2, canExposePayload) {
2792
2682
  if (message2.source === "web") {
2793
- const metadata2 = apiTurnMailboxMetadataSchema.safeParse(
2683
+ const metadata = apiTurnMailboxMetadataSchema.safeParse(
2794
2684
  message2.input.metadata
2795
2685
  );
2796
- if (!metadata2.success) return void 0;
2686
+ if (!metadata.success) return void 0;
2797
2687
  const text = message2.input.text.trim();
2798
2688
  if (!text) return void 0;
2799
2689
  return {
2800
2690
  createdAt: isoFromMs(message2.createdAtMs),
2801
2691
  delivery: message2.delivery,
2802
2692
  inboundMessageId: message2.inboundMessageId,
2803
- messageId: metadata2.data.messageId,
2693
+ messageId: metadata.data.messageId,
2804
2694
  receivedAt: isoFromMs(message2.receivedAtMs),
2805
2695
  role: "user",
2806
2696
  source: "web",
2807
2697
  ...canExposePayload ? {
2808
- actorIdentity: actorIdentityFromApiMetadata(metadata2.data),
2698
+ actorIdentity: actorIdentityFromApiMetadata(metadata.data),
2809
2699
  text
2810
2700
  } : { redacted: true }
2811
2701
  };
2812
2702
  }
2813
2703
  if (message2.source === "slack") {
2814
- const metadata2 = slackMailboxMetadataSchema.safeParse(
2704
+ const metadata = slackMailboxMetadataSchema.safeParse(
2815
2705
  message2.input.metadata
2816
2706
  );
2817
- if (!metadata2.success) return void 0;
2818
- if (metadata2.data.message.author.isMe === true) return void 0;
2707
+ if (!metadata.success) return void 0;
2708
+ if (metadata.data.message.author.isMe === true) return void 0;
2819
2709
  const text = message2.input.text.trim();
2820
2710
  if (!text) return void 0;
2821
2711
  if (!canExposePayload) {
@@ -2823,7 +2713,7 @@ async function projectPendingMessage(message2, canExposePayload) {
2823
2713
  createdAt: isoFromMs(message2.createdAtMs),
2824
2714
  delivery: message2.delivery,
2825
2715
  inboundMessageId: message2.inboundMessageId,
2826
- messageId: metadata2.data.message.id,
2716
+ messageId: metadata.data.message.id,
2827
2717
  receivedAt: isoFromMs(message2.receivedAtMs),
2828
2718
  redacted: true,
2829
2719
  role: "user",
@@ -2831,14 +2721,14 @@ async function projectPendingMessage(message2, canExposePayload) {
2831
2721
  };
2832
2722
  }
2833
2723
  const actorIdentity = await actorIdentityFromSlackMetadata(
2834
- metadata2.data,
2724
+ metadata.data,
2835
2725
  message2.destination?.platform === "slack" ? message2.destination.teamId : void 0
2836
2726
  );
2837
2727
  return {
2838
2728
  createdAt: isoFromMs(message2.createdAtMs),
2839
2729
  delivery: message2.delivery,
2840
2730
  inboundMessageId: message2.inboundMessageId,
2841
- messageId: metadata2.data.message.id,
2731
+ messageId: metadata.data.message.id,
2842
2732
  receivedAt: isoFromMs(message2.receivedAtMs),
2843
2733
  role: "user",
2844
2734
  source: "slack",
@@ -2889,8 +2779,8 @@ async function requireConversationPendingMessages(conversationId, options = {})
2889
2779
  }
2890
2780
 
2891
2781
  // src/api/conversations/stats.query.ts
2892
- import { and as and10, eq as eq11, gte, isNull as isNull4, lte, sql as sql7 } from "drizzle-orm";
2893
- import { alias as alias4 } from "drizzle-orm/pg-core";
2782
+ import { and as and9, eq as eq9, gte, isNull as isNull4, lte, sql as sql7 } from "drizzle-orm";
2783
+ import { alias as alias3 } from "drizzle-orm/pg-core";
2894
2784
 
2895
2785
  // src/api/conversations/aggregate.ts
2896
2786
  import { sql as sql6 } from "drizzle-orm";
@@ -2974,7 +2864,7 @@ function conversationActiveDaysColumn() {
2974
2864
 
2975
2865
  // src/api/conversations/stats.query.ts
2976
2866
  var WINDOW_DAYS = 90;
2977
- var treeConversation = alias4(juniorConversations, "stats_tree_conversation");
2867
+ var treeConversation = alias3(juniorConversations, "stats_tree_conversation");
2978
2868
  var treeAggregateColumns = conversationAggregateColumns({
2979
2869
  metrics: treeConversation,
2980
2870
  roots: juniorConversations
@@ -3033,7 +2923,7 @@ function statsItems(map) {
3033
2923
  );
3034
2924
  }
3035
2925
  function statsWhere(start, end) {
3036
- return and10(
2926
+ return and9(
3037
2927
  isNull4(juniorConversations.parentConversationId),
3038
2928
  gte(juniorConversations.lastActivityAt, start),
3039
2929
  lte(juniorConversations.lastActivityAt, end)
@@ -3117,7 +3007,7 @@ async function aggregateStats(db, start, end) {
3117
3007
  const [totalsRows, actorRows, locationRows, metricRows] = await Promise.all([
3118
3008
  db.select(treeAggregateColumns).from(juniorConversations).innerJoin(
3119
3009
  treeConversation,
3120
- eq11(
3010
+ eq9(
3121
3011
  treeConversation.rootConversationId,
3122
3012
  juniorConversations.conversationId
3123
3013
  )
@@ -3132,14 +3022,14 @@ async function aggregateStats(db, start, end) {
3132
3022
  ...treeAggregateColumns
3133
3023
  }).from(juniorConversations).innerJoin(
3134
3024
  treeConversation,
3135
- eq11(
3025
+ eq9(
3136
3026
  treeConversation.rootConversationId,
3137
3027
  juniorConversations.conversationId
3138
3028
  )
3139
3029
  ).leftJoin(
3140
3030
  juniorIdentities,
3141
- eq11(juniorIdentities.id, juniorConversations.actorIdentityId)
3142
- ).leftJoin(juniorUsers, eq11(juniorUsers.id, juniorIdentities.userId)).where(where).groupBy(
3031
+ eq9(juniorIdentities.id, juniorConversations.actorIdentityId)
3032
+ ).leftJoin(juniorUsers, eq9(juniorUsers.id, juniorIdentities.userId)).where(where).groupBy(
3143
3033
  juniorIdentities.displayName,
3144
3034
  juniorIdentities.emailNormalized,
3145
3035
  juniorIdentities.handle,
@@ -3157,13 +3047,13 @@ async function aggregateStats(db, start, end) {
3157
3047
  ...treeAggregateColumns
3158
3048
  }).from(juniorConversations).innerJoin(
3159
3049
  treeConversation,
3160
- eq11(
3050
+ eq9(
3161
3051
  treeConversation.rootConversationId,
3162
3052
  juniorConversations.conversationId
3163
3053
  )
3164
3054
  ).leftJoin(
3165
3055
  juniorDestinations,
3166
- eq11(juniorDestinations.id, juniorConversations.destinationId)
3056
+ eq9(juniorDestinations.id, juniorConversations.destinationId)
3167
3057
  ).where(where).groupBy(
3168
3058
  juniorConversations.channelName,
3169
3059
  juniorConversations.source,
@@ -3182,7 +3072,7 @@ async function aggregateStats(db, start, end) {
3182
3072
  tokens: treeAggregateColumns.tokens
3183
3073
  }).from(juniorConversations).innerJoin(
3184
3074
  treeConversation,
3185
- eq11(
3075
+ eq9(
3186
3076
  treeConversation.rootConversationId,
3187
3077
  juniorConversations.conversationId
3188
3078
  )
@@ -3209,8 +3099,8 @@ async function aggregateGuardianStats(db, start, end) {
3209
3099
  deny: sql7`COUNT(*) FILTER (WHERE ${decision} = 'deny')::integer`,
3210
3100
  requests: sql7`COUNT(*)::integer`
3211
3101
  }).from(juniorConversationEvents).where(
3212
- and10(
3213
- eq11(juniorConversationEvents.type, "guardian_action_reviewed"),
3102
+ and9(
3103
+ eq9(juniorConversationEvents.type, "guardian_action_reviewed"),
3214
3104
  gte(juniorConversationEvents.createdAt, start),
3215
3105
  lte(juniorConversationEvents.createdAt, end)
3216
3106
  )
@@ -3471,8 +3361,8 @@ function createConversationRoutes(options) {
3471
3361
  import { Hono as Hono2 } from "hono";
3472
3362
 
3473
3363
  // src/api/locations/query.ts
3474
- import { and as and11, asc as asc3, desc as desc3, eq as eq12, gte as gte2, isNull as isNull5, sql as sql8 } from "drizzle-orm";
3475
- import { alias as alias5 } from "drizzle-orm/pg-core";
3364
+ import { and as and10, asc as asc3, desc as desc3, eq as eq10, gte as gte2, isNull as isNull5, sql as sql8 } from "drizzle-orm";
3365
+ import { alias as alias4 } from "drizzle-orm/pg-core";
3476
3366
 
3477
3367
  // src/api/conversations/reporting.ts
3478
3368
  function surfaceLabel2(surface) {
@@ -3533,7 +3423,7 @@ function summaryFromRow(row, options = {}) {
3533
3423
  // src/api/locations/query.ts
3534
3424
  var RECENT_LIMIT = 25;
3535
3425
  var ACTIVITY_DAYS = 90;
3536
- var treeConversation2 = alias5(
3426
+ var treeConversation2 = alias4(
3537
3427
  juniorConversations,
3538
3428
  "location_tree_conversation"
3539
3429
  );
@@ -3579,10 +3469,10 @@ function topLevelWhere() {
3579
3469
  return isNull5(juniorConversations.parentConversationId);
3580
3470
  }
3581
3471
  function publicLocationWhere(destinationId) {
3582
- return and11(
3472
+ return and10(
3583
3473
  topLevelWhere(),
3584
- eq12(juniorDestinations.id, destinationId),
3585
- eq12(juniorDestinations.visibility, "public")
3474
+ eq10(juniorDestinations.id, destinationId),
3475
+ eq10(juniorDestinations.visibility, "public")
3586
3476
  );
3587
3477
  }
3588
3478
  function locationColumns() {
@@ -3633,13 +3523,13 @@ async function directoryRows(db) {
3633
3523
  ...conversationRangeColumns()
3634
3524
  }).from(juniorConversations).innerJoin(
3635
3525
  treeConversation2,
3636
- eq12(
3526
+ eq10(
3637
3527
  treeConversation2.rootConversationId,
3638
3528
  juniorConversations.conversationId
3639
3529
  )
3640
3530
  ).leftJoin(
3641
3531
  juniorDestinations,
3642
- eq12(juniorDestinations.id, juniorConversations.destinationId)
3532
+ eq10(juniorDestinations.id, juniorConversations.destinationId)
3643
3533
  ).where(topLevelWhere()).groupBy(...locationGroupBy());
3644
3534
  }
3645
3535
  async function directoryActivityRows(db, start) {
@@ -3653,8 +3543,8 @@ async function directoryActivityRows(db, start) {
3653
3543
  visibility: juniorDestinations.visibility
3654
3544
  }).from(juniorConversations).leftJoin(
3655
3545
  juniorDestinations,
3656
- eq12(juniorDestinations.id, juniorConversations.destinationId)
3657
- ).where(and11(topLevelWhere(), gte2(juniorConversations.lastActivityAt, start))).groupBy(date, juniorDestinations.visibility);
3546
+ eq10(juniorDestinations.id, juniorConversations.destinationId)
3547
+ ).where(and10(topLevelWhere(), gte2(juniorConversations.lastActivityAt, start))).groupBy(date, juniorDestinations.visibility);
3658
3548
  }
3659
3549
  function directoryActivityDays(rows, nowMs) {
3660
3550
  const days = /* @__PURE__ */ new Map();
@@ -3747,12 +3637,12 @@ async function recentLocationRows(db, locationId) {
3747
3637
  usage: juniorConversations.usage
3748
3638
  }).from(juniorConversations).innerJoin(
3749
3639
  juniorDestinations,
3750
- eq12(juniorDestinations.id, juniorConversations.destinationId)
3640
+ eq10(juniorDestinations.id, juniorConversations.destinationId)
3751
3641
  ).leftJoin(
3752
3642
  juniorIdentities,
3753
- eq12(juniorIdentities.id, juniorConversations.actorIdentityId)
3754
- ).leftJoin(juniorUsers, eq12(juniorUsers.id, juniorIdentities.userId)).where(
3755
- and11(
3643
+ eq10(juniorIdentities.id, juniorConversations.actorIdentityId)
3644
+ ).leftJoin(juniorUsers, eq10(juniorUsers.id, juniorIdentities.userId)).where(
3645
+ and10(
3756
3646
  publicLocationWhere(locationId),
3757
3647
  isNull5(juniorConversations.archivedAt)
3758
3648
  )
@@ -3779,27 +3669,27 @@ async function readLocationDetailFromSql(locationId, options = {}) {
3779
3669
  ...conversationRangeColumns()
3780
3670
  }).from(juniorConversations).innerJoin(
3781
3671
  treeConversation2,
3782
- eq12(
3672
+ eq10(
3783
3673
  treeConversation2.rootConversationId,
3784
3674
  juniorConversations.conversationId
3785
3675
  )
3786
3676
  ).innerJoin(
3787
3677
  juniorDestinations,
3788
- eq12(juniorDestinations.id, juniorConversations.destinationId)
3678
+ eq10(juniorDestinations.id, juniorConversations.destinationId)
3789
3679
  ).where(where).groupBy(...locationGroupBy()),
3790
3680
  getDb().select({
3791
3681
  date: activityDate,
3792
3682
  ...treeAggregateColumns2
3793
3683
  }).from(juniorConversations).innerJoin(
3794
3684
  treeConversation2,
3795
- eq12(
3685
+ eq10(
3796
3686
  treeConversation2.rootConversationId,
3797
3687
  juniorConversations.conversationId
3798
3688
  )
3799
3689
  ).innerJoin(
3800
3690
  juniorDestinations,
3801
- eq12(juniorDestinations.id, juniorConversations.destinationId)
3802
- ).where(and11(where, gte2(juniorConversations.lastActivityAt, start))).groupBy(activityDate),
3691
+ eq10(juniorDestinations.id, juniorConversations.destinationId)
3692
+ ).where(and10(where, gte2(juniorConversations.lastActivityAt, start))).groupBy(activityDate),
3803
3693
  getDb().select({
3804
3694
  actorIdentityId: juniorConversations.actorIdentityId,
3805
3695
  email: juniorUsers.primaryEmailNormalized,
@@ -3811,17 +3701,17 @@ async function readLocationDetailFromSql(locationId, options = {}) {
3811
3701
  ...treeAggregateColumns2
3812
3702
  }).from(juniorConversations).innerJoin(
3813
3703
  treeConversation2,
3814
- eq12(
3704
+ eq10(
3815
3705
  treeConversation2.rootConversationId,
3816
3706
  juniorConversations.conversationId
3817
3707
  )
3818
3708
  ).innerJoin(
3819
3709
  juniorDestinations,
3820
- eq12(juniorDestinations.id, juniorConversations.destinationId)
3710
+ eq10(juniorDestinations.id, juniorConversations.destinationId)
3821
3711
  ).leftJoin(
3822
3712
  juniorIdentities,
3823
- eq12(juniorIdentities.id, juniorConversations.actorIdentityId)
3824
- ).leftJoin(juniorUsers, eq12(juniorUsers.id, juniorIdentities.userId)).where(where).groupBy(
3713
+ eq10(juniorIdentities.id, juniorConversations.actorIdentityId)
3714
+ ).leftJoin(juniorUsers, eq10(juniorUsers.id, juniorIdentities.userId)).where(where).groupBy(
3825
3715
  juniorConversations.actorIdentityId,
3826
3716
  juniorUsers.primaryEmailNormalized,
3827
3717
  juniorUsers.displayName,
@@ -3934,22 +3824,22 @@ function createLocationRoutes() {
3934
3824
  import { Hono as Hono3 } from "hono";
3935
3825
 
3936
3826
  // src/api/people/list.query.ts
3937
- import { and as and13, eq as eq14, gte as gte3, sql as sql10 } from "drizzle-orm";
3827
+ import { and as and12, eq as eq12, gte as gte3, sql as sql10 } from "drizzle-orm";
3938
3828
 
3939
3829
  // src/api/people/shared.ts
3940
- import { and as and12, asc as asc4, desc as desc4, eq as eq13, isNull as isNull6, notExists, or as or5, sql as sql9 } from "drizzle-orm";
3941
- import { alias as alias6 } from "drizzle-orm/pg-core";
3830
+ import { and as and11, asc as asc4, desc as desc4, eq as eq11, isNull as isNull6, notExists, or as or4, sql as sql9 } from "drizzle-orm";
3831
+ import { alias as alias5 } from "drizzle-orm/pg-core";
3942
3832
  var RECENT_LIMIT2 = 25;
3943
3833
  var ACTIVITY_DAYS2 = 365;
3944
- var peopleTreeConversation = alias6(
3834
+ var peopleTreeConversation = alias5(
3945
3835
  juniorConversations,
3946
3836
  "people_tree_conversation"
3947
3837
  );
3948
- var peopleRootConversation = alias6(
3838
+ var peopleRootConversation = alias5(
3949
3839
  juniorConversations,
3950
3840
  "people_root_conversation"
3951
3841
  );
3952
- var peopleRootIdentity = alias6(juniorIdentities, "people_root_identity");
3842
+ var peopleRootIdentity = alias5(juniorIdentities, "people_root_identity");
3953
3843
  var peopleTreeAggregateColumns = conversationAggregateColumns({
3954
3844
  metrics: peopleTreeConversation,
3955
3845
  roots: juniorConversations
@@ -3957,37 +3847,37 @@ var peopleTreeAggregateColumns = conversationAggregateColumns({
3957
3847
  function peopleTreeMetricsJoin() {
3958
3848
  const rootOwnedByActor = getDb().select({ conversationId: peopleRootConversation.conversationId }).from(peopleRootConversation).innerJoin(
3959
3849
  peopleRootIdentity,
3960
- eq13(peopleRootIdentity.id, peopleRootConversation.actorIdentityId)
3850
+ eq11(peopleRootIdentity.id, peopleRootConversation.actorIdentityId)
3961
3851
  ).where(
3962
- and12(
3963
- eq13(
3852
+ and11(
3853
+ eq11(
3964
3854
  peopleRootConversation.conversationId,
3965
3855
  juniorConversations.rootConversationId
3966
3856
  ),
3967
3857
  isNull6(peopleRootConversation.parentConversationId),
3968
- eq13(
3858
+ eq11(
3969
3859
  peopleRootConversation.rootConversationId,
3970
3860
  peopleRootConversation.conversationId
3971
3861
  ),
3972
- eq13(
3862
+ eq11(
3973
3863
  peopleRootIdentity.emailNormalized,
3974
3864
  juniorUsers.primaryEmailNormalized
3975
3865
  ),
3976
- eq13(peopleRootIdentity.emailVerified, true)
3866
+ eq11(peopleRootIdentity.emailVerified, true)
3977
3867
  )
3978
3868
  );
3979
- return and12(
3980
- eq13(
3869
+ return and11(
3870
+ eq11(
3981
3871
  peopleTreeConversation.rootConversationId,
3982
3872
  juniorConversations.rootConversationId
3983
3873
  ),
3984
- or5(
3985
- eq13(
3874
+ or4(
3875
+ eq11(
3986
3876
  juniorConversations.rootConversationId,
3987
3877
  juniorConversations.conversationId
3988
3878
  ),
3989
- and12(
3990
- eq13(
3879
+ and11(
3880
+ eq11(
3991
3881
  peopleTreeConversation.conversationId,
3992
3882
  juniorConversations.conversationId
3993
3883
  ),
@@ -4037,11 +3927,11 @@ function statsItems2(map) {
4037
3927
  }
4038
3928
  function verifiedActorWhere(email) {
4039
3929
  const normalizedEmail = normalizeEmail(email);
4040
- return and12(
4041
- eq13(juniorIdentities.provider, "slack"),
4042
- eq13(juniorIdentities.emailVerified, true),
3930
+ return and11(
3931
+ eq11(juniorIdentities.provider, "slack"),
3932
+ eq11(juniorIdentities.emailVerified, true),
4043
3933
  sql9`${juniorUsers.primaryEmailNormalized} IS NOT NULL`,
4044
- normalizedEmail ? eq13(juniorUsers.primaryEmailNormalized, normalizedEmail) : void 0
3934
+ normalizedEmail ? eq11(juniorUsers.primaryEmailNormalized, normalizedEmail) : void 0
4045
3935
  );
4046
3936
  }
4047
3937
  async function recentActorRows(email) {
@@ -4064,12 +3954,12 @@ async function recentActorRows(email) {
4064
3954
  usage: juniorConversations.usage
4065
3955
  }).from(juniorConversations).innerJoin(
4066
3956
  juniorIdentities,
4067
- eq13(juniorIdentities.id, juniorConversations.actorIdentityId)
4068
- ).innerJoin(juniorUsers, eq13(juniorUsers.id, juniorIdentities.userId)).leftJoin(
3957
+ eq11(juniorIdentities.id, juniorConversations.actorIdentityId)
3958
+ ).innerJoin(juniorUsers, eq11(juniorUsers.id, juniorIdentities.userId)).leftJoin(
4069
3959
  juniorDestinations,
4070
- eq13(juniorDestinations.id, juniorConversations.destinationId)
3960
+ eq11(juniorDestinations.id, juniorConversations.destinationId)
4071
3961
  ).where(
4072
- and12(verifiedActorWhere(email), isNull6(juniorConversations.archivedAt))
3962
+ and11(verifiedActorWhere(email), isNull6(juniorConversations.archivedAt))
4073
3963
  ).orderBy(
4074
3964
  desc4(juniorConversations.lastActivityAt),
4075
3965
  asc4(juniorConversations.conversationId)
@@ -4113,17 +4003,17 @@ async function readPeopleListFromSql() {
4113
4003
  ...conversationRangeColumns()
4114
4004
  }).from(juniorConversations).innerJoin(
4115
4005
  juniorIdentities,
4116
- eq14(juniorIdentities.id, juniorConversations.actorIdentityId)
4117
- ).innerJoin(juniorUsers, eq14(juniorUsers.id, juniorIdentities.userId)).leftJoin(peopleTreeConversation, peopleTreeMetricsJoin()).where(verifiedActorWhere()).groupBy(juniorUsers.primaryEmailNormalized, juniorUsers.displayName),
4006
+ eq12(juniorIdentities.id, juniorConversations.actorIdentityId)
4007
+ ).innerJoin(juniorUsers, eq12(juniorUsers.id, juniorIdentities.userId)).leftJoin(peopleTreeConversation, peopleTreeMetricsJoin()).where(verifiedActorWhere()).groupBy(juniorUsers.primaryEmailNormalized, juniorUsers.displayName),
4118
4008
  getDb().select({
4119
4009
  activePeople: sql10`COUNT(DISTINCT ${juniorUsers.id})::int`,
4120
4010
  conversations: sql10`COUNT(*)::int`,
4121
4011
  date: activityDate
4122
4012
  }).from(juniorConversations).innerJoin(
4123
4013
  juniorIdentities,
4124
- eq14(juniorIdentities.id, juniorConversations.actorIdentityId)
4125
- ).innerJoin(juniorUsers, eq14(juniorUsers.id, juniorIdentities.userId)).where(
4126
- and13(
4014
+ eq12(juniorIdentities.id, juniorConversations.actorIdentityId)
4015
+ ).innerJoin(juniorUsers, eq12(juniorUsers.id, juniorIdentities.userId)).where(
4016
+ and12(
4127
4017
  verifiedActorWhere(),
4128
4018
  gte3(juniorConversations.lastActivityAt, start)
4129
4019
  )
@@ -4176,7 +4066,7 @@ async function readPeoplePluginReports(args) {
4176
4066
  source: "plugins"
4177
4067
  });
4178
4068
  }
4179
- const { getPluginProfileReports } = await import("./agent-hooks-TL2SGC5W.js");
4069
+ const { getPluginProfileReports } = await import("./agent-hooks-WTBPNRTC.js");
4180
4070
  return pluginOperationalReportFeedSchema.parse({
4181
4071
  generatedAt: new Date(nowMs).toISOString(),
4182
4072
  reports: await getPluginProfileReports({
@@ -4189,7 +4079,7 @@ async function readPeoplePluginReports(args) {
4189
4079
  }
4190
4080
 
4191
4081
  // src/api/people/profile.query.ts
4192
- import { and as and14, eq as eq15, gte as gte4, sql as sql11 } from "drizzle-orm";
4082
+ import { and as and13, eq as eq13, gte as gte4, sql as sql11 } from "drizzle-orm";
4193
4083
  function emptyProfile(email, nowMs) {
4194
4084
  const end = new Date(nowMs);
4195
4085
  end.setUTCHours(0, 0, 0, 0);
@@ -4268,15 +4158,15 @@ async function readPeopleProfileFromSql(email, options = {}) {
4268
4158
  ...peopleTreeAggregateColumns
4269
4159
  }).from(juniorConversations).innerJoin(
4270
4160
  juniorIdentities,
4271
- eq15(juniorIdentities.id, juniorConversations.actorIdentityId)
4272
- ).innerJoin(juniorUsers, eq15(juniorUsers.id, juniorIdentities.userId)).leftJoin(peopleTreeConversation, metricsJoin).where(where).groupBy(juniorUsers.primaryEmailNormalized, juniorUsers.displayName),
4161
+ eq13(juniorIdentities.id, juniorConversations.actorIdentityId)
4162
+ ).innerJoin(juniorUsers, eq13(juniorUsers.id, juniorIdentities.userId)).leftJoin(peopleTreeConversation, metricsJoin).where(where).groupBy(juniorUsers.primaryEmailNormalized, juniorUsers.displayName),
4273
4163
  getDb().select({
4274
4164
  date: activityDate,
4275
4165
  ...peopleTreeAggregateColumns
4276
4166
  }).from(juniorConversations).innerJoin(
4277
4167
  juniorIdentities,
4278
- eq15(juniorIdentities.id, juniorConversations.actorIdentityId)
4279
- ).innerJoin(juniorUsers, eq15(juniorUsers.id, juniorIdentities.userId)).leftJoin(peopleTreeConversation, metricsJoin).where(and14(where, gte4(juniorConversations.lastActivityAt, start))).groupBy(activityDate),
4168
+ eq13(juniorIdentities.id, juniorConversations.actorIdentityId)
4169
+ ).innerJoin(juniorUsers, eq13(juniorUsers.id, juniorIdentities.userId)).leftJoin(peopleTreeConversation, metricsJoin).where(and13(where, gte4(juniorConversations.lastActivityAt, start))).groupBy(activityDate),
4280
4170
  getDb().select({
4281
4171
  channel,
4282
4172
  channelName: juniorConversations.channelName,
@@ -4285,10 +4175,10 @@ async function readPeopleProfileFromSql(email, options = {}) {
4285
4175
  ...peopleTreeAggregateColumns
4286
4176
  }).from(juniorConversations).innerJoin(
4287
4177
  juniorIdentities,
4288
- eq15(juniorIdentities.id, juniorConversations.actorIdentityId)
4289
- ).innerJoin(juniorUsers, eq15(juniorUsers.id, juniorIdentities.userId)).leftJoin(peopleTreeConversation, metricsJoin).leftJoin(
4178
+ eq13(juniorIdentities.id, juniorConversations.actorIdentityId)
4179
+ ).innerJoin(juniorUsers, eq13(juniorUsers.id, juniorIdentities.userId)).leftJoin(peopleTreeConversation, metricsJoin).leftJoin(
4290
4180
  juniorDestinations,
4291
- eq15(juniorDestinations.id, juniorConversations.destinationId)
4181
+ eq13(juniorDestinations.id, juniorConversations.destinationId)
4292
4182
  ).where(where).groupBy(
4293
4183
  channel,
4294
4184
  juniorConversations.channelName,
@@ -4297,8 +4187,8 @@ async function readPeopleProfileFromSql(email, options = {}) {
4297
4187
  ),
4298
4188
  getDb().select({ surface, ...peopleTreeAggregateColumns }).from(juniorConversations).innerJoin(
4299
4189
  juniorIdentities,
4300
- eq15(juniorIdentities.id, juniorConversations.actorIdentityId)
4301
- ).innerJoin(juniorUsers, eq15(juniorUsers.id, juniorIdentities.userId)).leftJoin(peopleTreeConversation, metricsJoin).where(where).groupBy(surface),
4190
+ eq13(juniorIdentities.id, juniorConversations.actorIdentityId)
4191
+ ).innerJoin(juniorUsers, eq13(juniorUsers.id, juniorIdentities.userId)).leftJoin(peopleTreeConversation, metricsJoin).where(where).groupBy(surface),
4302
4192
  recentActorRows(normalizedEmail)
4303
4193
  ]);
4304
4194
  const totalsRow = totalsRows[0];
@@ -4376,7 +4266,7 @@ async function readPeopleProfile(email, options = {}) {
4376
4266
  }
4377
4267
 
4378
4268
  // src/api/people/spend.query.ts
4379
- import { and as and15, eq as eq16, gte as gte5, lte as lte2, sql as sql12 } from "drizzle-orm";
4269
+ import { and as and14, eq as eq14, gte as gte5, lte as lte2, sql as sql12 } from "drizzle-orm";
4380
4270
  var SEVEN_DAY_OFFSET = 6;
4381
4271
  var THIRTY_DAY_OFFSET = 29;
4382
4272
  function addUsd2(current, next) {
@@ -4405,9 +4295,9 @@ async function readPersonalSpendFromSql(email, nowMs = Date.now()) {
4405
4295
  date: activityDate
4406
4296
  }).from(juniorConversations).innerJoin(
4407
4297
  juniorIdentities,
4408
- eq16(juniorIdentities.id, juniorConversations.actorIdentityId)
4409
- ).innerJoin(juniorUsers, eq16(juniorUsers.id, juniorIdentities.userId)).leftJoin(peopleTreeConversation, metricsJoin).where(
4410
- and15(
4298
+ eq14(juniorIdentities.id, juniorConversations.actorIdentityId)
4299
+ ).innerJoin(juniorUsers, eq14(juniorUsers.id, juniorIdentities.userId)).leftJoin(peopleTreeConversation, metricsJoin).where(
4300
+ and14(
4411
4301
  verifiedActorWhere(normalizedEmail),
4412
4302
  gte5(juniorConversations.lastActivityAt, thirtyDayStart),
4413
4303
  lte2(juniorConversations.lastActivityAt, end)
@@ -4505,83 +4395,6 @@ function createPeopleRoutes() {
4505
4395
 
4506
4396
  // src/api/personal-tokens/routes.ts
4507
4397
  import { Hono as Hono4 } from "hono";
4508
-
4509
- // src/personal-tokens/store.ts
4510
- import { createHash, randomBytes, randomUUID } from "crypto";
4511
- import { and as and16, desc as desc5, eq as eq17, gt, isNull as isNull7 } from "drizzle-orm";
4512
- var TOKEN_PREFIX = "jr_pat_";
4513
- var TOKEN_SUFFIX_LENGTH = 8;
4514
- var DEFAULT_TOKEN_LIFETIME_MS = 90 * 24 * 60 * 60 * 1e3;
4515
- function normalizeEmail2(email) {
4516
- return email.trim().toLowerCase();
4517
- }
4518
- function hashToken(token2) {
4519
- return createHash("sha256").update(token2, "utf8").digest("hex");
4520
- }
4521
- function metadata(row) {
4522
- return {
4523
- id: row.id,
4524
- name: row.name,
4525
- tokenSuffix: row.tokenSuffix,
4526
- createdAt: row.createdAt.toISOString(),
4527
- expiresAt: row.expiresAt.toISOString(),
4528
- lastUsedAt: row.lastUsedAt?.toISOString() ?? null
4529
- };
4530
- }
4531
- async function createPersonalToken(args) {
4532
- const now = args.now ?? /* @__PURE__ */ new Date();
4533
- const token2 = `${TOKEN_PREFIX}${randomBytes(32).toString("base64url")}`;
4534
- const row = {
4535
- id: randomUUID(),
4536
- ownerEmailNormalized: normalizeEmail2(args.email),
4537
- name: args.name.trim(),
4538
- tokenHash: hashToken(token2),
4539
- tokenSuffix: token2.slice(-TOKEN_SUFFIX_LENGTH),
4540
- createdAt: now,
4541
- expiresAt: new Date(now.getTime() + DEFAULT_TOKEN_LIFETIME_MS)
4542
- };
4543
- await getDb().insert(juniorApiTokens).values(row);
4544
- return { ...metadata({ ...row, lastUsedAt: null, revokedAt: null }), token: token2 };
4545
- }
4546
- async function listPersonalTokens(email, now = /* @__PURE__ */ new Date()) {
4547
- const rows = await getDb().select().from(juniorApiTokens).where(
4548
- and16(
4549
- eq17(juniorApiTokens.ownerEmailNormalized, normalizeEmail2(email)),
4550
- isNull7(juniorApiTokens.revokedAt),
4551
- gt(juniorApiTokens.expiresAt, now)
4552
- )
4553
- ).orderBy(desc5(juniorApiTokens.createdAt));
4554
- return rows.map(metadata);
4555
- }
4556
- async function revokePersonalToken(args) {
4557
- const rows = await getDb().update(juniorApiTokens).set({ revokedAt: args.now ?? /* @__PURE__ */ new Date() }).where(
4558
- and16(
4559
- eq17(juniorApiTokens.id, args.id),
4560
- eq17(juniorApiTokens.ownerEmailNormalized, normalizeEmail2(args.email)),
4561
- isNull7(juniorApiTokens.revokedAt)
4562
- )
4563
- ).returning({ id: juniorApiTokens.id });
4564
- return rows.length > 0;
4565
- }
4566
- async function authenticatePersonalToken(token2, now = /* @__PURE__ */ new Date()) {
4567
- if (!token2.startsWith(TOKEN_PREFIX)) return void 0;
4568
- const rows = await getDb().select({
4569
- id: juniorApiTokens.id,
4570
- ownerEmailNormalized: juniorApiTokens.ownerEmailNormalized
4571
- }).from(juniorApiTokens).where(
4572
- and16(
4573
- eq17(juniorApiTokens.tokenHash, hashToken(token2)),
4574
- isNull7(juniorApiTokens.revokedAt),
4575
- gt(juniorApiTokens.expiresAt, now)
4576
- )
4577
- ).limit(1);
4578
- const match = rows[0];
4579
- if (!match) return void 0;
4580
- await getDb().update(juniorApiTokens).set({ lastUsedAt: now }).where(eq17(juniorApiTokens.id, match.id));
4581
- return match.ownerEmailNormalized;
4582
- }
4583
-
4584
- // src/api/personal-tokens/routes.ts
4585
4398
  function createPersonalTokenRoutes() {
4586
4399
  const app = new Hono4();
4587
4400
  app.get("/", requireViewer, async (context) => {
@@ -4805,6 +4618,105 @@ function createTaskRoutes() {
4805
4618
  return app;
4806
4619
  }
4807
4620
 
4621
+ // src/api/workspaces/routes.ts
4622
+ import { Hono as Hono7 } from "hono";
4623
+ function view(workspace) {
4624
+ return {
4625
+ id: workspace.id,
4626
+ name: workspace.name,
4627
+ setupScript: workspace.setupScript,
4628
+ repos: workspace.repos.map((repo) => ({
4629
+ provider: repo.provider,
4630
+ repo: repo.repo,
4631
+ checkoutPath: workspaceRepoCheckoutPath(repo.repo),
4632
+ isPrimary: repo.isPrimary
4633
+ }))
4634
+ };
4635
+ }
4636
+ function handleValidationError(error) {
4637
+ if (error instanceof WorkspaceValidationError) {
4638
+ throwApiError(400, error.message);
4639
+ }
4640
+ throw error;
4641
+ }
4642
+ function createWorkspaceRoutes() {
4643
+ const app = new Hono7();
4644
+ app.get("/", requireViewer, async () => {
4645
+ return jsonResponse(workspaceListSchema, {
4646
+ workspaces: (await listWorkspaces(getDb())).map(view)
4647
+ });
4648
+ });
4649
+ app.post(
4650
+ "/",
4651
+ requireViewer,
4652
+ validateRequest("json", workspaceBodySchema, "Invalid request body."),
4653
+ async (context) => {
4654
+ const body = context.req.valid("json");
4655
+ try {
4656
+ const workspace = await createWorkspace(body);
4657
+ return jsonResponse(workspaceSchema, view(workspace), { status: 201 });
4658
+ } catch (error) {
4659
+ handleValidationError(error);
4660
+ }
4661
+ }
4662
+ );
4663
+ app.get(
4664
+ "/:id",
4665
+ requireViewer,
4666
+ validateRequest(
4667
+ "param",
4668
+ workspaceParamsSchema,
4669
+ "Invalid route parameters."
4670
+ ),
4671
+ async (context) => {
4672
+ const { id } = context.req.valid("param");
4673
+ const workspace = await getWorkspace(getDb(), id);
4674
+ if (!workspace) throwApiError(404, "Workspace not found.");
4675
+ return jsonResponse(workspaceSchema, view(workspace));
4676
+ }
4677
+ );
4678
+ app.put(
4679
+ "/:id",
4680
+ requireViewer,
4681
+ validateRequest(
4682
+ "param",
4683
+ workspaceParamsSchema,
4684
+ "Invalid route parameters."
4685
+ ),
4686
+ validateRequest("json", workspaceBodySchema, "Invalid request body."),
4687
+ async (context) => {
4688
+ const { id } = context.req.valid("param");
4689
+ const body = context.req.valid("json");
4690
+ try {
4691
+ const workspace = await updateWorkspace(id, body);
4692
+ if (!workspace) throwApiError(404, "Workspace not found.");
4693
+ return jsonResponse(workspaceSchema, view(workspace));
4694
+ } catch (error) {
4695
+ handleValidationError(error);
4696
+ }
4697
+ }
4698
+ );
4699
+ app.delete(
4700
+ "/:id",
4701
+ requireViewer,
4702
+ validateRequest(
4703
+ "param",
4704
+ workspaceParamsSchema,
4705
+ "Invalid route parameters."
4706
+ ),
4707
+ async (context) => {
4708
+ const { id } = context.req.valid("param");
4709
+ if (!await deleteWorkspace(id)) {
4710
+ throwApiError(404, "Workspace not found.");
4711
+ }
4712
+ return jsonResponse(deleteWorkspaceResponseSchema, {
4713
+ deleted: true
4714
+ });
4715
+ }
4716
+ );
4717
+ return app;
4718
+ }
4719
+
4808
4720
  // src/api/stats.ts
4809
4721
  var WINDOW_DAYS2 = 90;
4810
4722
  async function readStatsReport() {
@@ -4834,7 +4746,7 @@ function readDescriptionText(home) {
4834
4746
  }
4835
4747
  }
4836
4748
  async function readSkillReports() {
4837
- const { discoverSkills } = await import("./skills-3UDJJXSO.js");
4749
+ const { discoverSkills } = await import("./skills-KYPSHSQR.js");
4838
4750
  const skills = await discoverSkills();
4839
4751
  return skillReportsSchema.parse(
4840
4752
  skills.map((skill) => ({
@@ -4844,7 +4756,7 @@ async function readSkillReports() {
4844
4756
  );
4845
4757
  }
4846
4758
  async function readPlugins() {
4847
- const { pluginCatalogRuntime } = await import("./catalog-runtime-IGSMIADJ.js");
4759
+ const { pluginCatalogRuntime } = await import("./catalog-runtime-CZ2SQINY.js");
4848
4760
  return pluginsSchema.parse(
4849
4761
  pluginCatalogRuntime.getProviders().map((plugin) => ({
4850
4762
  configKeys: plugin.manifest.configKeys ?? [],
@@ -4857,7 +4769,7 @@ async function readPlugins() {
4857
4769
  async function readRuntimeInfoReport() {
4858
4770
  const [{ homeDir }, { pluginCatalogRuntime }, plugins, skills] = await Promise.all([
4859
4771
  import("./discovery-GUFTFBTL.js"),
4860
- import("./catalog-runtime-IGSMIADJ.js"),
4772
+ import("./catalog-runtime-CZ2SQINY.js"),
4861
4773
  readPlugins(),
4862
4774
  readSkillReports()
4863
4775
  ]);
@@ -4873,7 +4785,7 @@ async function readRuntimeInfoReport() {
4873
4785
  }
4874
4786
  async function readPluginOperationalReportFeed() {
4875
4787
  const nowMs = Date.now();
4876
- const { getPluginOperationalReports } = await import("./agent-hooks-TL2SGC5W.js");
4788
+ const { getPluginOperationalReports } = await import("./agent-hooks-WTBPNRTC.js");
4877
4789
  return pluginOperationalReportFeedSchema.parse({
4878
4790
  source: "plugins",
4879
4791
  generatedAt: new Date(nowMs).toISOString(),
@@ -4883,7 +4795,7 @@ async function readPluginOperationalReportFeed() {
4883
4795
 
4884
4796
  // src/api.ts
4885
4797
  function createJuniorApi() {
4886
- const app = new Hono7();
4798
+ const app = new Hono8();
4887
4799
  app.get(
4888
4800
  "/api/health",
4889
4801
  async () => jsonResponse(healthReportSchema, readHealthReport())
@@ -4922,6 +4834,7 @@ function createJuniorApi() {
4922
4834
  app.route("/api/locations", createLocationRoutes());
4923
4835
  app.route("/api/user-pages", createUserPageRoutes());
4924
4836
  app.route("/api/tasks", createTaskRoutes());
4837
+ app.route("/api/workspaces", createWorkspaceRoutes());
4925
4838
  app.notFound(
4926
4839
  () => jsonResponse(
4927
4840
  apiErrorSchema,